473,395 Members | 1,504 Online
Bytes | Software Development & Data Engineering Community
Post Job

Home Posts Topics Members FAQ

Join Bytes to post your question to a community of 473,395 software developers and data experts.

Modern C++: confused with constructors inheritance

I guess I've been out of C++ for a while, since right now I don't seem
to get a simple solution for overriding inherited constrictors.

What worked in Borland C++ & Pascal (and Java, if I remember correctly) as:
-------------------------------------------
class Base { public: Base(); };
Base::Base() { printf("Base"); }

class Derived : Base { public: Derived(); override; };
Derived::Derived() { /*inherited;*/ printf("Derived"); }

void main() { Derived d; }

///
would return "Derived"
-------------------------------------------
I could control whether I wanted to use base constructor or not with
keywords "override" and "inherited" (if I took the comments out from the
Derived constructor).

But in VC++ the keyword "override" is not defined, and no matter what I
do with constructors, results are always the same:
-------------------------------------------
class Base { public: Base(); };
Base::Base() { printf("Base"); }
class Derived : Base { public: Derived(); };
Derived::Derived() { printf("Derived"); }

void main() { Derived d; }

would return "BaseDerived"
-------------------------------------------

Is there any way to make the derived constructor fully override the
base? I tried all combinations with public/protected/private to no
avail. Something very simple without an intricate C++ implementation,
that only hardcore C++ folks can understand?

I'm somewhat confused here.

Jul 19 '05 #1
7 13603
> But in VC++ the keyword "override" is not defined, and no matter what I
do with constructors, results are always the same:
-------------------------------------------
class Base { public: Base(); };
Base::Base() { printf("Base"); }
class Derived : Base { public: Derived(); };
Derived::Derived() { printf("Derived"); }

void main() { Derived d; }

would return "BaseDerived"
-------------------------------------------
derived is not a C++ keyword, and I certainly haven't seen it anywhere in
C++.
Is there any way to make the derived constructor fully override the
base? I tried all combinations with public/protected/private to no
avail. Something very simple without an intricate C++ implementation,
that only hardcore C++ folks can understand?
Overriding a constructor would be a very bad idea. It totally violates any
encapsulation. Why exactly do you need to do it? I don't think I've ever
seen any OOP language that has this ability. And I suspect this is a
tautology, insomuch that any language with this functionality could not be
OO.

I'm somewhat confused here.


You and me both :¬)

Cheers,

4Space
Jul 19 '05 #2
Beach Potato wrote:
I guess I've been out of C++ for a while, since right now I don't seem
to get a simple solution for overriding inherited constrictors.
Constructors cannot be inherited or overridden (since they cannot be
virtual).

What worked in Borland C++ & Pascal (and Java, if I remember correctly) as:
-------------------------------------------
class Base { public: Base(); };
Base::Base() { printf("Base"); }

class Derived : Base { public: Derived(); override; };
'override' is not defined.
Derived::Derived() { /*inherited;*/ printf("Derived"); }

void main() { Derived d; }
In C++, main returns int. void has never been an acceptable return type
for main.

After fixing your code, it printed "BaseDerived" which is what I
expected. The default Base constructor is used to initialize the 'Base'
part of d.

///
would return "Derived"
-------------------------------------------
I could control whether I wanted to use base constructor or not with
keywords "override" and "inherited" (if I took the comments out from the
Derived constructor).
I'm not aware of any way you could have achieved that in C++. override
and inherited have never been C++ keywords, to the best of my knowledge.

But in VC++ the keyword "override" is not defined, and no matter what I
do with constructors, results are always the same:
-------------------------------------------
class Base { public: Base(); };
Base::Base() { printf("Base"); }
class Derived : Base { public: Derived(); };
Derived::Derived() { printf("Derived"); }

void main() { Derived d; }

would return "BaseDerived"
Technically the behavior is undefined, but after fixing the obvious
problems that would be the expected output.
-------------------------------------------

Is there any way to make the derived constructor fully override the
base? I tried all combinations with public/protected/private to no
avail. Something very simple without an intricate C++ implementation,
that only hardcore C++ folks can understand?


There is no way at all. At least not in those terms. I mean, I'm sure
what you want to finally accomplish is possible, but not via overriding
constructors, since that is not possible in C++. It also doesn't make
sense - the 'Base' part of a 'Derived' object must be initialized
somehow. The constructor is how that happens. You can use whatever
constructor you want (by 'calling' it in the initialization list for
'Derived's constructor), but if you don't specify, the default will be
used. If there is no default, the program will fail to compile.

Basically the question is (as it often is in this group): What do you
*really* want to do?

-Kevin
--
My email address is valid, but changes periodically.
To contact me please use the address from a recent posting.

Jul 19 '05 #3
On Thu, 11 Sep 2003 20:06:54 +0530, "Josephine Schafer" <js*@usa.net> wrote:

"jeffc" <no****@nowhere.com> wrote in message
news:3f********@news1.prserv.net...

There isn't *any* way to override constructors, with the given language
elements. Overriding constructors would require virtual constructors, and
that doesn't exist in C++. Do a search on "virtual constructor" to see if
you can find a simulation of this behavior.


Well, Scott Meyers does discuss simulatiom of virtual constructors in More
Effective C++ (Item 25).
May be that help the OP.

Virtual constructors as well as dynamic binding during initialization
(DBDI) / dynamic binding during construction (DBDC) are also in the FAQ.

Unfortunately not collected into a single topic.

But perhaps we're the discussing the wrong thing; if I recall correctly
the OP asked about _inherited constrictors_, i.e. the monster snakes.

Jul 19 '05 #4
4Space wrote:
But in VC++ the keyword "override" is not defined, and no matter what I
do with constructors, results are always the same:
-------------------------------------------
class Base { public: Base(); };
Base::Base() { printf("Base"); }
class Derived : Base { public: Derived(); };
Derived::Derived() { printf("Derived"); }

void main() { Derived d; }

would return "BaseDerived"
-------------------------------------------

derived is not a C++ keyword, and I certainly haven't seen it anywhere in
C++.


I was talking about words "override" and "inherited", that do exist in
some OOP languages. In Pascal, for instance, the default behaviour is to
"override" the constructor (so this keyword is not included in the
language), so you have to specify when and where in the constructor you
want to call the base, like:

constructor Derived.Init;
begin
Other_Func();
inherited Init;
end;

In this case, for instance, you call it after you initialization, not
before. Or you can even not call it at all. That makes you responsible,
of course, for the initialization of all Base variables.

4Space wrote: Overriding a constructor would be a very bad idea. It totally violates any
encapsulation. Why exactly do you need to do it?
Kevin Goodsell wrote: Basically the question is (as it often is in this group): What do you
*really* want to do?


A typical example - a class that implements Microsoft Windows window. If
you place the initialization routines in a Base constructor, it
registers the default window class and then creates the actual window.
If you derive a class to represent a different type of a window, you
could hope that the Derived constructor would do a different routine,
and that you'll create a single new window, not both - Derived and Base.
So I guess, if unability to break the execution is a C++ limitation or
feature, and constructors are not a good place to run class-specific
initialization procedures.
Jul 19 '05 #5
On Thu, 11 Sep 2003 19:36:48 GMT, Beach Potato <wi*************************@yahoo.com> wrote:
Kevin Goodsell wrote:
Basically the question is (as it often is in this group): What do you
*really* want to do?
A typical example - a class that implements [a] window. If
you place the initialization routines in a Base constructor, it
registers the default window class and then creates the actual window.
If you derive a class to represent a different type of a window, you
could hope that the Derived constructor would do a different routine,
and that you'll create a single new window, not both - Derived and Base.
So I guess, if unability to break the execution is a C++ limitation or
feature


It is a feature; see the FAQ 23.3
<url:http://www.parashift.com/c++-faq-lite/strange-inheritance.html#faq-23.3>

and constructors are not a good place to run class-specific initialization
procedures.


On the contrary, that's exactly where class-specific initialization should
be.

Unfortunately most C++ GUI frameworks have been inspired by less typesafe
languages, but here's one way (and the way I prefer) for doing exactly the
kind of thing that you _really_ want to do, in a typesafe manner:
class GeneralWindow
{
protected:
WindowHandle myHandle;

class ApiWindowFactory
{
public:
virtual WindowHandle create() const { /*...*/ }
};
public:
GeneralWindow( ApiWindowFactory const& aFactory = ApiWindowFactory() )
{
// ...
myHandle = aFactory.create();
}
};
class Button: public GeneralWindow
{
protected:
typedef GeneralWindow Base;

class ApiButtonFactory: public Base::ApiWindowFactory
{
public:
virtual WindowHandle create() const { /*...*/ }
};
public:
Button( ApiButtonFactory const& aFactory = ApiButtonFactory() )
: Base( aFactory )
{
}
};
See also the FAQ 23.4
<url:http://www.parashift.com/c++-faq-lite/strange-inheritance.html#faq-23.4>

(Heya Marshall, t'was a good thing to include that, not? But although that
discussion's over, wrt. to 'init' method I'd still like to see a reference to
<url:http://www.research.att.com/~bs/3rd_safe.pdf> section E.3.5, on why
an 'init'-method is generally a very very bad idea, not to say "evil"... ;-) )

Jul 19 '05 #6
> A typical example - a class that implements Microsoft Windows window. If
you place the initialization routines in a Base constructor, it
registers the default window class and then creates the actual window.
If you derive a class to represent a different type of a window, you
could hope that the Derived constructor would do a different routine,
and that you'll create a single new window, not both - Derived and Base.
Well, I'm not sure exactly what you are trying to do. But perhaps
parameterised protected constructors would help - allowing your derived
classes to pass more information to the base class object. It may just be
that aggregation rather than inheritance is what you want.
So I guess, if unability to break the execution is a C++ limitation or
feature, and constructors are not a good place to run class-specific
initialization procedures.


Like Alf said - constructors *ARE* the place to do this. But base classes
are responsible for deciding what derived classes can an cannot change.

Cheers

4Space
Jul 19 '05 #7
On Thu, 11 Sep 2003 19:36:48 GMT, Beach Potato
<wi*************************@yahoo.com> wrote:
4Space wrote:
But in VC++ the keyword "override" is not defined, and no matter what I
do with constructors, results are always the same:
-------------------------------------------
class Base { public: Base(); };
Base::Base() { printf("Base"); }
class Derived : Base { public: Derived(); };
Derived::Derived() { printf("Derived"); }

void main() { Derived d; }

would return "BaseDerived"
-------------------------------------------

derived is not a C++ keyword, and I certainly haven't seen it anywhere in
C++.


I was talking about words "override" and "inherited", that do exist in
some OOP languages. In Pascal, for instance, the default behaviour is to
"override" the constructor (so this keyword is not included in the
language), so you have to specify when and where in the constructor you
want to call the base, like:

constructor Derived.Init;
begin
Other_Func();
inherited Init;
end;

In this case, for instance, you call it after you initialization, not
before. Or you can even not call it at all. That makes you responsible,
of course, for the initialization of all Base variables.


This can't really work in C++. C++ has a much more strict construction
model due to the existence of "value" types. When you enter your
constructor body, all your bases and all your members have already
been constructed. As a result, if a base class constructor does
something in particular, then all classes derived from that are stuck
with it. Hence, if the base class needs to be configurable, it should
be via passed in parameters that the derived classes can create as
they like.

In the languages you are talking about, can the derived class
constructors modify the value of base class private members? If so,
I'd consider the feature extremely dangerous, and if not, it's a bit
useless.

4Space wrote:
Overriding a constructor would be a very bad idea. It totally violates any
encapsulation. Why exactly do you need to do it?
Kevin Goodsell wrote:
Basically the question is (as it often is in this group): What do you
*really* want to do?


A typical example - a class that implements Microsoft Windows window. If
you place the initialization routines in a Base constructor, it
registers the default window class and then creates the actual window.


Are you saying that this Window is hard coded, and can't be modified
to a Window of choice by passing different parameters to the
constructor? That sounds like a useless Window base class...
If you derive a class to represent a different type of a window, you
could hope that the Derived constructor would do a different routine,
and that you'll create a single new window, not both - Derived and Base.
So I guess, if unability to break the execution is a C++ limitation or
feature, and constructors are not a good place to run class-specific
initialization procedures.


On the contrary, constructors are an excellent place to do
initialization, since it allows you to increase the number of class
invariants which should help reduce bugs. However, you can't hard code
behaviour in the constructor if you want it to be modifiable by
derived classes - make the behaviour configurable by passing in
different parameters.

Tom
Jul 19 '05 #8

This thread has been closed and replies have been disabled. Please start a new discussion.

Similar topics

4
by: Jimmy Johns | last post by:
Hi, I have some classes as follows: #include <iostream> using namespace std; class A { public: virtual A* clone() const = 0; };
5
by: Jochen Zeischka | last post by:
Hello, I just tried something with multiple inheritance and I have a problem with the construction of my object. There's a base class Base, containing an integer. The base class has 2 derived...
1
by: Russ Ford | last post by:
Hi all, I'm trying to get inheritance and constructors clear in my head (and in my code). I have the following inheritance situation (all derivations public): A is the base class B is...
3
by: hazz | last post by:
The following classes follow from the base class ' A ' down to the derived class ' D ' at the bottom of the inheritance chain. I am calling the class at the bottom, "public class D" from a client...
10
by: Kevin Buchan | last post by:
I searched the news group and could not find an answer to this question, so I'll go ahead and post it. Let's say I have a class A with a couple different constructors... nothin' special. Now,...
7
by: eric | last post by:
hello i'm confused by an example in the book "Effective C++ Third Edition" and would be grateful for some help. here's the code: class Person { public: Person(); virtual ~Person(); // see...
7
by: Adam Nielsen | last post by:
Hi everyone, I'm having some trouble getting the correct chain of constructors to be called when creating an object at the bottom of a hierarchy. Have a look at the code below - the inheritance...
7
by: Pep | last post by:
I'm getting weird results at the moment so thought I'd rebase my knowledge of c++ storage with your help :) I have a class used as a type in a struct and the struct is handled by a 3rd party...
6
by: Peng Yu | last post by:
Hi, I want B has all the constructors that A has. Obviously, the code below would not work. I could define a corresponding B's constructor for each A's constructor. But if A has many...
0
by: ryjfgjl | last post by:
In our work, we often receive Excel tables with data in the same format. If we want to analyze these data, it can be difficult to analyze them because the data is spread across multiple Excel files...
0
by: emmanuelkatto | last post by:
Hi All, I am Emmanuel katto from Uganda. I want to ask what challenges you've faced while migrating a website to cloud. Please let me know. Thanks! Emmanuel
0
BarryA
by: BarryA | last post by:
What are the essential steps and strategies outlined in the Data Structures and Algorithms (DSA) roadmap for aspiring data scientists? How can individuals effectively utilize this roadmap to progress...
1
by: nemocccc | last post by:
hello, everyone, I want to develop a software for my android phone for daily needs, any suggestions?
1
by: Sonnysonu | last post by:
This is the data of csv file 1 2 3 1 2 3 1 2 3 1 2 3 2 3 2 3 3 the lengths should be different i have to store the data by column-wise with in the specific length. suppose the i have to...
0
by: Hystou | last post by:
There are some requirements for setting up RAID: 1. The motherboard and BIOS support RAID configuration. 2. The motherboard has 2 or more available SATA protocol SSD/HDD slots (including MSATA, M.2...
0
marktang
by: marktang | last post by:
ONU (Optical Network Unit) is one of the key components for providing high-speed Internet services. Its primary function is to act as an endpoint device located at the user's premises. However,...
0
Oralloy
by: Oralloy | last post by:
Hello folks, I am unable to find appropriate documentation on the type promotion of bit-fields when using the generalised comparison operator "<=>". The problem is that using the GNU compilers,...
0
jinu1996
by: jinu1996 | last post by:
In today's digital age, having a compelling online presence is paramount for businesses aiming to thrive in a competitive landscape. At the heart of this digital strategy lies an intricately woven...

By using Bytes.com and it's services, you agree to our Privacy Policy and Terms of Use.

To disable or enable advertisements and analytics tracking please visit the manage ads & tracking page.