473,804 Members | 3,031 Online
Bytes | Software Development & Data Engineering Community
+ Post

Home Posts Topics Members FAQ

copy ctor question

Given this class heirarchy

class Base{};

class A : public Base
{};

class B : public Base
{};

etc

How do I go about coding a copy ctor for the following class:

class SomeClass
{
std::vector<Bas e*> m_BasePointers;
};

when m_BasePointers contains pointers to child classes of Base?


thanks
Jul 19 '05 #1
39 2894
scooter wrote:
Given this class heirarchy

class Base{};

class A : public Base
{};

class B : public Base
{};

etc

How do I go about coding a copy ctor for the following class:

class SomeClass
{
std::vector<Bas e*> m_BasePointers;
};

when m_BasePointers contains pointers to child classes of Base?


Do you want to copy what Base* points to? Well, that is not very simple...
I mean it is, but forcing it work isn't (you cannot force people to write
correct code).

// I hope you have meant:
class Base{
virtual ~Base();
};

// Now let's add a clone function:
class Base{
virtual ~Base();
virtual Base *Clone() const {
return new Base(*this);
}
};
class A : public Base
{
virtual A *Clone() const{
return new A(*this);
}
};

class B : public Base
{
virtual B *Clone() const{
return new B(*this);
}
};

The trouble with that is that if someone forgets to write his clone in a
derived class you get slicing. :-(

Now all you need to do is to use Base::Clone() to copy the elements.

Some please add testing using the RTTI into the base class(es) to check if
*this is actually a Base when the function is called. If not, they assert
(abort).

--
Attila aka WW
Jul 19 '05 #2
scooter wrote:
Given this class heirarchy

class Base{};

class A : public Base
{};

class B : public Base
{};

etc

How do I go about coding a copy ctor for the following class:

class SomeClass
{
std::vector<Bas e*> m_BasePointers;
};

when m_BasePointers contains pointers to child classes of Base?


I'm assuming you want the Base-derived objects to be copied in the process?
Because if just copying the pointer values is what you want the copy
constructor of std::vector should already do the trick.

Your best option (IMHO) is probably to give Base a 'clone' function, that
you implement in A and B to create new (equivalent) As and Bs, and use that
in the copy constructor of SomeClass:

<code>
class Base
{
public:
virtual Base* Clone() const = 0;
};

class A : public Base
{
public:
A(A &a) { /*copy const for A*/ }
virtual Base* Clone() const
{
/* Caller must delete pointer! */
return new A(*this);
}
};

/* Same for B as for A */
</code>

Writing the copy constructor should be easy then.

--
Unforgiven

A: Top Posting!
Q: What is the most annoying thing on Usenet?

Jul 19 '05 #3
> class B : public Base
{
virtual B *Clone() const{
return new B(*this);
}
};


Well, your solution is the prototype pattern. A good idea can be the
implementation of the copy-constructor, because you are using it:
class B : public Base
{
public:
B( const B& b )
{
...
}

virtual B *Clone() const{
return new B(*this); // Here the copy-constructor is used.
}
};
Ralf
http://www.oop-trainer.de

Jul 19 '05 #4
The solution described by Attila Feher is the prototype pattern of the GoF.
The idea is to give a polymorphic (virtual) method, which can create a copy
of your polymorphic object. The problem is, that a constructor never can be
virtual.
You have to call it by its correct name, which ist the class name. Copying a
polymorphic object with the constructor would force you to find out the
object type
before you are copying. This is the reason for the virtual clone() method.
A good idea is to use the copy-constructor inside the clone() method.
Ralf

http://www.oop-trainer.de

Jul 19 '05 #5
Ralf Schneeweiß wrote:
class B : public Base
{
virtual B *Clone() const{
return new B(*this);
}
};


Well, your solution is the prototype pattern. A good idea can be the
implementation of the copy-constructor, because you are using it:


And since the class contains absolutely no managed resources the copy
constructor syntetized by the compiler is just fine.

--
Attila aka WW
Jul 19 '05 #6
Ralf Schneeweiß wrote:
The solution described by Attila Feher is the prototype pattern of
the GoF. The idea is to give a polymorphic (virtual) method, which
can create a copy of your polymorphic object.
It is very similar, but the motivation is completely different. Therefore
it looks like the Prototype pattern, but it isn't. One reason for that is
that it is not used to provide copies of prototypes.
The problem is, that a constructor never can be virtual.
Which does not matter for use, since we use polymorphic behavior, so we do
not work with constructors directly.
You have to call it by its correct name,
which ist the class name.
Which does not apply here, since we do not know the class name.
Copying a polymorphic object with the constructor would
force you to find out the object type before you are copying.
This is the reason for the virtual clone()
method. A good idea is to use the copy-constructor inside the clone()
method.


It *is* using the copy constructor.

--
Attila aka WW
Jul 19 '05 #7

"Attila Feher" <at**********@l mf.ericsson.se> wrote in message
news:bl******** **@newstree.wis e.edt.ericsson. se...
Ralf Schneeweiß wrote:
The solution described by Attila Feher is the prototype pattern of
the GoF. The idea is to give a polymorphic (virtual) method, which
can create a copy of your polymorphic object.
It is very similar, but the motivation is completely different. Therefore
it looks like the Prototype pattern, but it isn't. One reason for that is
that it is not used to provide copies of prototypes.
The problem is, that a constructor never can be virtual.


Which does not matter for use, since we use polymorphic behavior, so we do
not work with constructors directly.
You have to call it by its correct name,
which ist the class name.


Which does not apply here, since we do not know the class name.
Copying a polymorphic object with the constructor would
force you to find out the object type before you are copying.
This is the reason for the virtual clone()
method. A good idea is to use the copy-constructor inside the clone()
method.


It *is* using the copy constructor.

--
Attila aka WW


I think you're misunderstandin g Ralf's intention. If *I'm* understanding it
correctly, he's not disagreeing with you, but rather providing an
explanantion as to why yours is a good solution. At least, that's what I
got out of it. (The statement "the problem is..." isn't a complaint about
your solution, but an explanantion of the problem that *led* to the
solution.) Ralf, forgive me if I'm wrong, but that is what you meant, isn't
it?

(BTW, what's "GoF"???)

-Howard


Jul 19 '05 #8
Attila Feher wrote:
Ralf Schneeweiß wrote:
class B : public Base
{
virtual B *Clone() const{
return new B(*this);
}
};


Well, your solution is the prototype pattern. A good idea can be the
implementatio n of the copy-constructor, because you are using it:

And since the class contains absolutely no managed resources the copy
constructor syntetized by the compiler is just fine.


Keep the copy ctor, because you'll probably end up adding
data to the class, and at sometime you'll have a debugging
session where you'll want to know when the damn thing is
copy conbstructed.

Kick out the inlines though, virtual inlines are definitely
a mistake, and the rest are a waste of time, and only serve
to clutter your headers with implementation details.

Jul 19 '05 #9
WW
lilburne wrote:
Well, your solution is the prototype pattern. A good idea can be the
implementation of the copy-constructor, because you are using it:

Again: it is not the Prototype pattern, it just happens to look like it.
The motivation of the Protoype pattern is completely different from the
motivation here. The things this code copies are not prototypes.
And since the class contains absolutely no managed resources the copy
constructor syntetized by the compiler is just fine.

Keep the copy ctor, because you'll probably end up adding
data to the class, and at sometime you'll have a debugging
session where you'll want to know when the damn thing is
copy conbstructed.


Big mistake. Huge mistake. Adding a copy constructor to a class having no
controlled resources is a mistake. It's copy constructor will be identical
to the one generated by the compiler - at best. However it introduces
maintenance risk and nightmare for no value.

If someone needs to know when a class is copied that person can look at the
language definition. Or make a small, 15 lines test program if unsure. BTW
copy constructors with side effects are rarely a good idea.
Kick out the inlines though, virtual inlines are definitely
a mistake, and the rest are a waste of time, and only serve
to clutter your headers with implementation details.


Have you looked at the language definition lately? I do not recall virtual
inlines being a mistake. And writing things inline in an untested example
code does not mean that they have to be written inline in real code
either...

BTW such a clone function is "final". So making it inline is not a mistake.
Although in this case adds not much, since such a function will only be
called via a pointer to (some) base. For this (by you unmentioned) reason
it makes sense not to make them inline. BTW I hope you did know that
virtual functions (if the dynamic type is known compile time) *can* be
inlined.

--
WW aka Attila
Jul 19 '05 #10

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

Similar topics

11
2345
by: Sam Wilson [Bentley] | last post by:
If you pass a C++ object by value as an argument to a function which has a variable-length argument list (...), the MSVC7 C++ compiler does not call the object's copy constructor and will not complain if the copy constructor is private. 1) Is this part of the C++ language definition? What is the thinking behind it? 2) In any case, how can I catch at compile time any callers that try to
5
4247
by: kalita | last post by:
template<class T> class A { template<class Y> A(const A<Y> &) { // whatever } };
5
1699
by: nagrik | last post by:
Hello group, Last week I picked up a thread, which pointed out that if a copy constructor is created with pointers instead of reference, there is a danger of it going in infinite recursion. My observation: 1. Compiler does not complain.
1
2129
by: blangela | last post by:
3.0 Advanced Topic Addendum There are a few cases where the C++ compiler cannot provide an overloaded assignment operator for your class. If your class contains a const member or/and a reference member, the compiler will not be able to synthesize an assignment operator for your class. It actually helps to think of a reference member as a const member (since it cannot be made to reference any other object once it has been initialized). ...
10
4032
by: campos | last post by:
"Effective C++ 3rd Edition" Item 6, P39 ------------------------------------------------------- class Uncopyable { protected: // allow construction Uncopyable() {} // and destruction of ~Uncopyable() {} // derived objects... private: Uncopyable(const Uncopyable&); // ...but prevent copying
13
2483
by: Jeroen | last post by:
Hi all, I'm trying to implement a certain class but I have problems regarding the copy ctor. I'll try to explain this as good as possible and show what I tried thusfar. Because it's not about a certain code syntax but more a 'code architecture' thing , I'll use simple example classes (which are certainly not complete or working...) just to illustrate the idea (and I may make some mistakes because I'm not that experienced...). The...
6
1582
by: Richard Thompson | last post by:
Hi - I have a program which was previously working (but wasn't well tested). I've added a new function call, and it now doesn't compile. The call requires a copy constructor, but the compiler appears to think that it actually calls one of the *other* constructors. The copy ctor would work in this context, but the other ctor can't be used (it leads to a template instantiation error, which the compiler is reporting).
3
2060
by: subramanian100in | last post by:
If we provide any ctor for a class the compiler does not supply the default ctor. However if we do not provide the copy ctor but provide any other ctor, the compiler still supplies the copy ctor. Why doesn't the compiler supply the default ctor but still supplies the copy ctor when we have defined any other ctor ? Kindly explain
2
2167
by: subramanian100in | last post by:
If we do not provide any ctor for a class, the compiler provides the default ctor and copy ctor if needed. Consider a class Test. Suppose we provide some ctor in class Test but do not provide the default ctor. Suppose we try to create Test obj;
11
2294
by: Dijkstra | last post by:
Hi folks! First, this is the code I'm using to expose the problem: ------------------------------------------------------------------ #include <functional> #include <string> #include <iostream> using namespace std;
0
9706
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, people are often confused as to whether an ONU can Work As a Router. In this blog post, we’ll explore What is ONU, What Is Router, ONU & Router’s main usage, and What is the difference between ONU and Router. Let’s take a closer look ! Part I. Meaning of...
0
9579
by: Hystou | last post by:
Most computers default to English, but sometimes we require a different language, especially when relocating. Forgot to request a specific language before your computer shipped? No problem! You can effortlessly switch the default language on Windows 10 without reinstalling. I'll walk you through it. First, let's disable language synchronization. With a Microsoft account, language settings sync across devices. To prevent any complications,...
0
10571
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, it seems that the internal comparison operator "<=>" tries to promote arguments from unsigned to signed. This is as boiled down as I can make it. Here is my compilation command: g++-12 -std=c++20 -Wnarrowing bit_field.cpp Here is the code in...
0
10326
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 tapestry of website design and digital marketing. It's not merely about having a website; it's about crafting an immersive digital experience that captivates audiences and drives business growth. The Art of Business Website Design Your website is...
0
9143
agi2029
by: agi2029 | last post by:
Let's talk about the concept of autonomous AI software engineers and no-code agents. These AIs are designed to manage the entire lifecycle of a software development project—planning, coding, testing, and deployment—without human intervention. Imagine an AI that can take a project description, break it down, write the code, debug it, and then launch it, all on its own.... Now, this would greatly impact the work of software developers. The idea...
1
7615
isladogs
by: isladogs | last post by:
The next Access Europe User Group meeting will be on Wednesday 1 May 2024 starting at 18:00 UK time (6PM UTC+1) and finishing by 19:30 (7.30PM). In this session, we are pleased to welcome a new presenter, Adolph Dupré who will be discussing some powerful techniques for using class modules. He will explain when you may want to use classes instead of User Defined Types (UDT). For example, to manage the data in unbound forms. Adolph will...
0
6851
by: conductexam | last post by:
I have .net C# application in which I am extracting data from word file and save it in database particularly. To store word all data as it is I am converting the whole word file firstly in HTML and then checking html paragraph one by one. At the time of converting from word file to html my equations which are in the word document file was convert into image. Globals.ThisAddIn.Application.ActiveDocument.Select();...
0
5520
by: TSSRALBI | last post by:
Hello I'm a network technician in training and I need your help. I am currently learning how to create and manage the different types of VPNs and I have a question about LAN-to-LAN VPNs. The last exercise I practiced was to create a LAN-to-LAN VPN between two Pfsense firewalls, by using IPSEC protocols. I succeeded, with both firewalls in the same network. But I'm wondering if it's possible to do the same thing, with 2 Pfsense firewalls...
1
4295
by: 6302768590 | last post by:
Hai team i want code for transfer the data from one system to another through IP address by using C# our system has to for every 5mins then we have to update the data what the data is updated we have to send another system

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.