Instantiating Derived objects from the Base class - c++

Trying to create a Driver type class where, below, Base is the Driver that is passed a type at instantiation. The type, the 2 in this case, is used to construct the correct derived object.
My compiler is throwing a Declaration syntax error on the "Class Base" line.
My end goal is to be able to do this:
Base *B;
B = new Base(2);
if(B)
{
B->DoStuff();
B->DoMoreStuff();
delete B;
}
Here is my code that won't compile...
class Base
{
public:
Base(int h);
virtual ~Base();
private:
int hType;
Base *hHandle;
};
class Derived1 : public Base
{
public:
Derived1();
virtual ~Derived1();
};
class Derived2 : public Base
{
public:
Derived2();
virtual ~Derived2();
};
Base::Base(int h)
{
hType = h;
switch(h)
{
case 1:
hHandle = new Derived1;
break;
case 2:
hHandle = new Derived2;
break;
}
}
Derived1::Derived1():Base(1)
{
printf("\nDerived1 Initialized\n\n");
}
Derived2::Derived2():Base(2)
{
printf("\nDerived2 Initialized\n\n");
}
Below is updated code to show the full source. I think I now understand why it will not compile. As is pointed out below, I have an endless loop of calls to 'new'
#include <stdio.h>
class Base
{
public:
Base();
Base(int h);
Create (int h);
virtual ~Base();
private:
int hType;
Base *hHandle;
};
class Derived1 : public Base
{
public:
Derived1();
virtual ~Derived1();
};
class Derived2 : public Base
{
public:
Derived2();
virtual ~Derived2();
};
Base::Base()
{
}
Base::Base(int h)
{
Create(h);
}
Base::Create(int h)
{
hType = h;
switch(h)
{
case 1:
hHandle = new Derived1;
break;
case 2:
hHandle = new Derived2;
break;
}
}
Derived1::Derived1()
{
printf("\nDerived1 Initialized\n\n");
}
Derived2::Derived2()
{
printf("\nDerived2 Initialized\n\n");
}

It looks like you're trying to do a class factory.
I'd recommend that you have a static method in Base that returns either Derived1 or Derived2.
class Base
{
public:
static Base* Create(int);
virtual void DoStuff() = 0;
}
class Derived1 : public Base
{
Derived1()
{
printf("\nDerived1 Initialized\n\n");
}
virtual void DoStuff()
{
}
}
class Derived2 : public Base
{
Derived2()
{
printf("\nDerived2 Initialized\n\n");
}
virtual void DoStuff()
{
}
}
Base* Base::Create(int n)
{
if (n==1)
return new Derived1();
else if (n==2)
return new Derived2();
else
return nullptr;
}
void main()
{
Base* B = Base::Create(2);
if(B)
{
B->DoStuff();
delete B;
}
}

Related

Memory issue in casting from a Derived class to a Base class

I have a class Base and another class Derived (derived from Base).
Also I have a 2 functions GetValue(Base*) and GetDerivedValue(Derived*).
Now, from the main() function, I have access to only GetValue(), but I need the value of both Base and Derived classes.
class Base
{
public:
Base ()
{
abc =0;
}
~Base ()
{
abc =0;
}
int abc;
};
class Derived : public Base
{
public:
Derived ()
{
def =0;
}
~Derived ()
{
def =0 ;
}
int def;
};
int GetDerivedValue (int &def)
{
def = 5;
}
int GetValue (Base *&pbase)
{
Derived *d = new Derived ();
GetDerivedValue (d->def);
pbase = (Base *) d;
}
int main ()
{
Base *pbase = NULL;
GetValue (pbase);
// Goal here is to get the avlue of def as 5 without any memory issue
}
Where should I release the pointers to make sure there is no memory errors?
I think you are looking for something like this:
class Base
{
public:
Base() : abc(0) {}
virtual ~Base() {}
int abc;
};
class Derived : public Base
{
public:
Derived() : def(0) {}
~Derived() {}
int def;
};
void GetDerivedValue(int &def)
{
def = 5;
}
void GetValue(Base* &pbase)
{
Derived *d = new Derived;
GetDerivedValue(d->def);
pbase = d;
}
int main()
{
Base *pbase = NULL;
GetValue(pbase);
// use pbase as needed...
delete pbase;
}
Which would be better written using std::unique_ptr instead:
#include <memory>
class Base
{
public:
virtual ~Base() = default;
int abc = 0;
};
class Derived : public Base
{
public:
int def = 0;
};
void GetDerivedValue(int &def)
{
def = 5;
}
std::unique_ptr<Base> GetValue()
{
auto d = std::make_unique<Derived>();
GetDerivedValue(d->def);
return d;
}
int main()
{
auto pbase = GetValue();
// use pbase as needed...
}

How to correctly initialize different derived class in switch statement?

I have the following code, with a class hierarchy structure of a base class Base, and several derived class Derived1, Derived2, Derived3...so on.
switch(i){
case 1:{
Derived1* d1;
generateD1(d1);
otherFunc(d1); //function signature is otherFunc(Base*)
break;
}
case 2:{
Derived2* d2;
generateD2(d2);
otherFunc(d2);
break;
}
... //goes on for many cases
}
How can I use the inheritance mechanism to improve the above codes?
Something like this:
class Base
{
public:
virtual ~Base() {}
virtual void generate() = 0 {}
virtual void other() = 0 {}
};
class Derived1 : public Base
{
public:
virtual void generate() override {}
virtual void other() override {}
};
class Derived2 : public Base
{
public:
virtual void generate() override {}
virtual void other() override {}
};
int main()
{
int i;
Base *b;
switch(i)
{
case 1:
b = new Derived1;
break;
case 2:
b = new Derived2;
break;
...
}
b->generate();
b->other();
...
delete b;
return 0;
}
You could drop the generate() method and just use constructors:
class Base
{
public:
virtual ~Base() {}
virtual void other() = 0 {}
};
class Derived1 : public Base
{
public:
Derived1() {}
virtual void other() override {}
};
class Derived2 : public Base
{
public:
Derived2() {}
virtual void other() override {}
};
int main()
{
int i;
Base *b;
switch(i)
{
case 1:
b = new Derived1;
break;
case 2:
b = new Derived2;
break;
...
}
b->other();
...
delete b;
return 0;
}
FYI, in addition to #SidS 's solution, we can also extract the generating process as a simple function which returns a pointer of Base as follows.
Here I also use std::unique_ptr which makes our code more safe with RAII semantics and then you can omit calling delete b:
#include <stdexcept>
#include <memory>
std::unique_ptr<Base> create(int i) // C++11
{
switch(i)
{
case 1:
return std::make_unique<Derived1>(); // C++14
break;
case 2:
return std::make_unique<Derived2>();
break;
default:
throw std::logic_error("unsupported.");
}
}
Then the caller side would be more simple one as follows:
DEMO
auto b = create(i);
b->generate();
b->other();

two children has same implementation of F() , other two children has different implementation of F, all four derive from same class

I have the following class hierarchy.
class Base
{
virtual void F();
}
class Derived1 : public Base
{
void F() {
cout<< " one implementation"<<endl;
}
}
class Derived2 : public Base
{
void F() {
cout<< " one implementation"<<endl;
}
}
class Derived3 : public Base
{
void F() {
cout<< " other implementation"<<endl;
}
}
class Derived4 : public Base
{
void F() {
cout<< " other implementation"<<endl;
}
}
Introducing more classes in the hierarchy like following seems to solve the issue
class Base
{
virtual void F();
}
class Base1 : public Base {
void F() {
cout<< " one implementation"<<endl;
}
}
class Base2 : public Base {
void F() {
cout<< " other implementation"<<endl;
}
}
class Derived1 : public Base1
{
}
class Derived2 : public Base1
{
}
class Derived3 : public Base2
{
}
class Derived4 : public Base2
{
}
I was wondering if the above use case of few siblings having same implementation than other siblings can be tackled better? Is there any obvious design pattern which i am missing here?
If F is the only functionality i want may be I can solve it just by composition( see below). I do not know whether it is a good idea to do that.
composition
class Base
{
virtual void F();
}
class Base1 : public Base {
void F() {
cout<< " one implementation"<<endl;
}
}
class Base2 : public Base {
void F() {
cout<< " other implementation"<<endl;
}
}
class Derived1
{
Base * Fer;
Derived1()
{
Fer = new Base1();
}
}
class Derived2
{
Base * Fer;
Derived1()
{
Fer = new Base1();
}
}
class Derived3
{
Base * Fer;
Derived1()
{
Fer = new Base2();
}
}
class Derived4
{
Base * Fer;
Derived1()
{
Fer = new Base2();
}
}
I would use composition, but this way:
#include <iostream>
// define an interface
class Base
{
virtual void F() = 0;
};
// define an implementation framework which pulls in templated
// components to do the work
template<class HandleF>
struct Impl : Base
{
virtual void F() override {
f_handler(this);
}
HandleF f_handler;
};
struct OneImplementationOfF
{
template<class Self>
void operator()(Self* self) const
{
std::cout<< " one implementation"<< std::endl;
}
};
struct OtherImplementationOfF
{
template<class Self>
void operator()(Self* self) const
{
std::cout<< " other implementation"<< std::endl;
}
};
// now build our classes
class Derived1 : public Impl<OneImplementationOfF>
{
};
class Derived2 : public Impl<OneImplementationOfF>
{
};
class Derived3 : public Impl<OtherImplementationOfF>
{
};
class Derived4 : public Impl<OtherImplementationOfF>
{
};

How to get rid of duplicate code in derived classes?

I have a class hierarchy like:
class A {
list<A*> children;
public:
void update() {
do_something();
update_current();
for(auto child : children)
children->update();
}
protected:
virtual void update_current() {};
};
class B : public A {
protected:
void update_current() override {
do_something_important();
};
};
class C1 : public B {
protected:
void update_current() override {
B::update_current();
do_something_very_important();
};
};
class C2 : public B {
protected:
void update_current() override {
B::update_current();
do_something_very_important_2();
};
};
int main() {
A* a = new A();
//fill a's childred list somehow
while(come_condition) {
//some code
a.update();
//something else
}
return 0;
}
The question is: how can I remove duplicate B::update_current(); calls from derived classes without changing program's behaviour? Is it possible or are there no solutions except calling base class functions manually? Thank you.
You could make B's children override a different function:
class B : public A {
protected:
void update_current() override final {
do_something_important();
do_something_important_later();
};
virtual void do_something_important_later() = 0;
};
With:
class C2 : public B {
protected:
void do_something_important_later() override {
do_something_very_important_2();
};
};

C++ reference in base class constructor

I have a logic in base class constructor. The result of the logic has to be captured in the derived class constructor in a temporary variable. Is there a way to do it?
For example
class Base
{
Base() { int temp_value = some_logic; }
};
class Derived : public Base
{
Derived() { // need the temp value here.. }
};
Thanks,
Gokul.
I guess the easiest way I can think of would be to just separate some_logic into it's own method...
class Base
{
Base() { int temp_value = initializationLogic(); }
int initializationLogic(){ return some-logic;}
};
class Derived : public Base
{
Derived() { int temp_value_here_too = initializationLogic(); }
};
Either:
class Base
{
protected int not_so_temp_value;
Base() { not_so_temp_value = some_logic_result; }
};
class Derived : public Base
{
Derived() { // read the not_so_temp_value member here.. }
};
Or:
class Base
{
Base(int some_logic_result) { int temp_value = some_logic; }
};
class Derived : public Base
{
static Derived* create()
{
int some_logic_result = some_logic;
return new Derived(some_logic_result);
}
Derived(int some_logic_result) : Base(some_logic_result)
{ // use the some_logic_result here.. }
};
This is the one i am planning to use
class Base
{
Base(int& some_logic_result) { some_logic_result = some_logic; }
};
class Derived : public Base
{
Derived(int some_logic_result = 0) : Base(some_logic_result)
{ // use the some_logic_result here.. }
};
Thanks,
Gokul.