If given a parent class A that contains a defined Destructor, will B-it's child- execute it when creating a B object? even if I did not create manually nor inherit the A's Destructor in the B class?
I expect that it will since I saw it in a video tutorial of c++ but do not understand why? Because the Constructor was manually inherited!
The compiler always implements a destructor for your class, if you haven't declared one. The compiler also generates code that calls base class destructors.
In other words, base class destructors are not inherited but get called from after your derived class destructor.
See Destructor:
Destruction sequence
For both user-defined or implicitly-defined destructors, after the body of the destructor is executed, the compiler calls the destructors for all non-static non-variant members of the class, in reverse order of declaration, then it calls the destructors of all direct non-virtual base classes in reverse order of construction (which in turn call the destructors of their members and their base classes, etc), and then, if this object is of most-derived class, it calls the destructors of all virtual bases.
Even when the destructor is called directly (e.g. obj.~Foo();), the return statement in ~Foo() does not return control to the caller immediately: it calls all those member and base destructors first.
The child class inherits the data members and member function of parent class but private members remain inaccesible in child class.Only Public member function and data members are accecible in child class.In Inheritance constructor or destructor is not inherited by child class but in the child class constructor and destructor there is an explicit call to base class constructor and destructor.
whenever we create an object of child class ,first constructoe of base class will be invoked then constructor of derived class is called.while if the object of child class is destroyed the destructor of child class will be invoked first and then destructor of parent class will be called.
Related
I am having trouble understanding virtual functions. When I overload a virtual function, is the new derived function called only? Or both derived and base functions? Because I noticed that when virtual destructors are called, the base AND the derived class destructors are called.
destructors are special member functions in this particular regards.
If you have a virtual base class destructor then it will properly call Base as well as derived class destructors during polymorphic deletion(calling delete on base class pointer pointinf to derived class object.).
However, Other virtual member functions do not share the same special status as destructors. Only the function defined for the appropriate object type gets called. If you need any other function to be called you need to do so explicitly.
a derived class object is nothing but a kind of wrapper to the base class object.
So in case of destructors,both the destructors should be called which is an expected behaviour.
In case of virtual function, you are given a chance to replace the function in a base class.so using a base class pointer to hold a derived class object will only call the virtual function in the derived class.
I am new in C++ and I have just started studying polymorphism. I know that if I create an object for the derived class then the constructor of both derived and base class is get called. Does it mean that, when I create an object for the derived class, eventually I am ending up with two objects- one is created by the constructor of base class and another one created by the constructor of derived class?
Can anyone explain, what is the job of base class constructor when I want to create an object for the derived class.
The job of the base class constructor is to initialise the base class member variables (consider the case of a private member variable in the base class).
When you call a constructor for a derived object, you only end up with one object. The base class constructor initialises the base class parts of the new object, and the derived constructor initialises the derived class parts of the same new object.
Constructors do not allocate space and initiate instances of objects; they initialise the object immediately after space has been allocated.
When you declare a object on the stack or use new first the memory is reserved and object is created, then the constructors are executed, starting with the base constructor and working upwards towards the most derived class.
You will end up with a derived class object, that contains a base class object.
Constructors don't magically create another instance of an object. They initialise a certain piece of memory, but calling a constructor and allocating memory are not the same thing -- the latter is either done behind the scenes (for objects with automatic and static storage duration) or with new and malloc (for objects with dynamic storage duration).
EDIT: Before I get angry comments about it: "behind the scenes" is a vague way to put it; the definition of an object with automatic or static storage duration ensures that it gets memory.
Whether you are creating an object of the base class or derived class, you end up with one object.
Just because the base class constructor is called, it doesn't mean you get one extra object for that call. Here, the base class constructor will be executed, which typically sets attributes of the base class. The object on the whole would be composed of the base class properties and derived class properties.
If you have a class then you would have to define a contructor or constructors (there are certain circumstances in where you do not have to). A constructor has the purpose to initialise the class data members, you give a value to its data members. Any data member that you do not give it a value, will have an undefined value unless the data member is an instance of a class that happens to have a default constructor.
So when you create an instance of that class, the compiler will invoke the appropriate constructor, and the members of the instance that you have just created will have data initialised with values as you set them in the constructor.
If you have a derived class, you can add data members to it, but remember that it has also an inherited member: the base class. So when you define a constructor in you derived class, you must invoke a constructor of the base class (so that the members of the base class get fully initialised) and assign value to the derived class own data members.
So you create an instance of the derived class, the derived class constructor is invoved. As part of its functionality it invokes the constructor of its base class (so you might say two constructors but this is the wrong of viewing it).
If you create an instance of the base class, only that constructor is invoked.
When we create an object, Constructor will be called. Its not when constructor called object is being created.
You can assume Creating object as a function and Constructor is another function which is called inside it.
Assume A is a base class and B is a derived class,
class A
{
}
class B : public A
{
}
We will be creating object for class A in below ways,
A obja;
or
A obja = new A();
In both cases you can assume a function Create is getting called,
A::Create()
{
A();
}
If you are creating Derived class B object then Create method of B will be called,
So internally Create method of B will look like below,
B::Create()
{
B();
A();
}
So when we create Derived class object first derived class initialization happens and then Base class initialization happen. It not means object is created twice.
Object will be created for the Call where you are creating object using.
B obj;
or
B obj = new B();
Calling the constructors are internal functionality as Constructors called in the Create function.
Note : Create function in the above code is done only for illustrative purpose.
when object of a derived class is created then constructor function of that class will be created first then to use the constructor function of the base class will be called by a separate object at the time of calling it will be invoked by that object.
This question already has answers here:
Do I need to explicitly call the base virtual destructor?
(7 answers)
Closed 7 years ago.
Please consider the following:
class base{
base();
~base();
}:
class derived : public base{
};
Does a base class destructor get automatically invoked when a derived object is destructed when the derived class has no destructor defined?
Otherwise, if I DO have a destructor in the derived class too, do I have to call the base class destructor explicitly?
class base{
base();
~base();
}:
class derived : public base{
derived();
~derived{
base::~base(); //do I need this?
}
};
The base class destructor is automatically invoked in this case; you do not need to call it.
However, note that when destroying an object through delete on a base class pointer and the destructor is not virtual, the result is going to be undefined behavior (although you might not get a crash).
Always declare the destructor as virtual in any class which is meant to be derived from. If the base class does not need to have a destructor, include a virtual one anyway with an empty body.
There is an exception to the above rule for an edge case: if your derived classes do not need to support polymorphic destruction, then the destructor does not need to be virtual. In this case it would be correct to make it protected instead; more details here, but be advised that this rarely occurs in practice.
Does a base class destructor is automatically invoked when a derived object is destructed and the derived class has no destructor defined?
Yes, the Base class destructor is automatically invoked after the Derived class Destructor, irrespective of Derived class destructor being explicitly defined or not.
Otherwise, if I have a destructor in the derived class too, do I need to call explicitly base class destructor too?
No, You don't need to.
There will not be any scenario in C++, where one has to explicitly invoke a destructor except while using placement new.
No, base destructors are invoked automatically in this case, in much the same way that base constructors are can be invoked automatically.
Note, though, that if you are using polymorphism and destroying through a base pointer, you should make sure that the destructor is virtual otherwise this will break.
You should never invoke a base class destructor from a derived class destructor.
The reason is base class destructor will be then called automatically for the second time and writing destructors in such way that this doesn't cause problem is problematic - see this question.
Is there any difference between a protected and a private destructor in C++? If a base classes destructor is private, I imagine that it is still called when deleting the derived class object.
If the base class destructor is private or protected then you cannot call delete through the base-class pointer.
Use a protected destructor to prevent the destruction of a derived object via a base-class pointer. It limits access to the destuctor to derived classes. And it prevents automatic
(stack) objects of class base.
In effect it is used to allow any
other polymorphic use of derived
classes via pointers to base, but not
allow the users to delete using such a
pointer. Example:- Abstract Base Classes / Interfaces.
But a protected, non-virtual destructor on a non-final class seems to be a bug waiting to happen. Assuming you do not provide a destroy() function, you have to eventually make the dtor public. As soon as you do that, you have no further control over the class, and run the risk of polymorphic deletion with a non-virtual dtor, if someone derives further from your class.
Taken from here:
If the constructor/destructor is declared as private, then the class cannot be instantiated.
This is true, however it can be instantiated from another method in the class. Similarly, if the destructor is private, then the object can only be deleted from inside the class as well. Also, it prevents the class from being inherited (or at least, prevent the inherited class from being instantiated/destroyed at all).
The following piece of code will result in the compiler error (VC2010):
C2248: 'base::~base' : cannot access private member declared in class 'base'
class base
{
~base(){}
};
class derived : public base
{
};
int main ()
{
derived* d = new derived;
delete d;
}
However, if you change the base destructor to be protected, everything works fine.
The answer is that your assumption is wrong. The base class destructor cannot be called when it is private.
I have a class called MyBase which has a constructor and destructor:
class MyBase
{
public:
MyBase(void);
~MyBase(void);
};
and I have a class called Banana, that extends MyBase like so:
class Banana:public MyBase
{
public:
Banana(void);
~Banana(void);
};
Does the implementation of the new constructor and destructor in Banana override the MyBase ones, or do they still exist, and get called say before or after the Banana constructor / destructor executes?
Thanks, and my apologies if my question seems silly.
A Base constructor will always be called before the derived constructor.
The Base destructor will be called after Dervided destructor.
You can specify on derived constructor which Base constructor you want, if not the default one will be executed.
If you define other constructors but not default and don't specify on Derived constructor which one to execute it'll try default which doesn't exist and will crash compilation.
The above happens because once you declare one constructor no default constructors are generated.
Constructors cannot be overriden. You can't declare a base class constructor in a derived class. A class constructor has to call a constructor in base class (if one is not explicitly stated, the default constructor is called) prior to anything else.
To be able to clean up the derived class correctly, you should declare the base class destructor as virtual:
virtual ~MyBase() { ... }
It should say
class Banana : public MyBase
{
public:
Banana(void);
~Banana(void);
};
The constructor of the derived class gets called after the constructor of the base class. The destructors get called in reversed order.
The constructors are called top down in the inheritance tree. This is so that the derived constructor can count on the base object being fully initialized before it tries to use any properties of the base.
Destructors are called in reverse order of the constructors, for the same reason - the derived classes depend on the base, but the base doesn't depend on the derived.
If there is any possibility of destroying the object through a pointer to a base class, you must declare all of the destructors virtual.
Constructors and destructors are special member functions. In general you will read everywhere that construction starts from the least derived type all the way in the hierarchy down to the most derived type. This is actually the order in which constructor execution completes, but not how construction is started.
Constructors initialization list execution order guarantees that while the most derived object's constructor will be the first constructor to start executing it will be the last constructor to complete
When you instantiate an object the most derived constructor that matches the construction call gets called first. The initialization list of the matched most derived constructor starts, and initialization lists have a fixed order: first the constructors of the base classes in order or appearance within the inheritance list get called. Then the member attribute constructors are called in the order in which they appear in the class declaration (not the order in which they appear in the initialization list). After the whole initialization list (at each level) completes, the constructor body block is executed, after which the constructor call completes.
All base destructors will be called in reverse order of construction after the most derived destructor has completed execution. Destruction happens in exact reverse order of construction.
Destructors are special in a different way: they cannot be overriden. When you call the most derived destructor of a class, it will complete the execution of the destructor body, after which all member attribute destructors will be called in reverse order of creation. After the most derived destructor has completed and so have done the member destructors of the most derived object, the destructor of its most direct bases start in reverse order of construction, the destructor bodies will execute, then the member attributes destructors and so on... At the end all constructed elements will be destroyed.
Destructors for polymorphic classes should be virtual
The destruction description above starts with the call to the most derived destructor. This can be achieved by calling delete on a pointer to the most derived type, when an auto object goes out of scope or when the object is deleted through a base class whose destructor is virtual.
If you forget to add the destructor keyword in the base class and you try to delete a derived object through a pointer to the base you will call the base destructor directly, and that implies that all sub objects below the pointer type in the hierarchy will not be properly destroyed. All inheritance hierarchies in which you will delete objects through pointers to a base type must have virtual destructors. As a general rule of thumb, if you already have any virtual method, the cost of making the destructor virtual is negligible and is a safe net. Many coding guides enforce that destructors in inheritance hierarchies must be virtual. Some go as far as requesting all destructors to be virtual, This has the intention of avoiding possible resource leaks at the cost of adding a vtable for all types and an vtable pointer for all objects.
You are missing the type of inheritance:
Change
class Banana:MyBase
To:
class Banana: public MyBase
As for
does the implementation of the new
constructor and destructor in Banana
override the MyBase ones, or do they
still exist, and get called say before
or after the Banana constructor /
destructor executes?
The order of inherited executes from bottom to top, that means that MyBase will be called first, then Banana. If you had another subclass, it would be called last.
Take this example:
class RottenBanana : public Banana
The inheritance chain is now RottenBanana -> Banana -> MyBase
The constructors of this class will be called starting at MyBase, then Banana and then calling RottenBanana.
If you instantiate an EEGModeRGB object (which has tri-color led's attached) - then immediately delete it you'd see the colors Blue, Green, Yellow, and Red, for one second each - in that order.
class EEGMode {
public:
EEGMode() { setAllPixelsToColor(BLUE); delay(1000); }
virtual ~EEGMode() { setAllPixelsToColor(RED); delay(1000); }
};
class EEGModeRGB : public EEGMode {
public:
EEGModeRGB() { setAllPixelsToColor(GREEN); delay(1000); }
virtual ~EEGModeRGB() { setAllPixelsToColor(YELLOW); delay(1000); }
};