Overloading operator=( )
-
I'm trying to better understand how operator=() overloading works. I have the following code:
CBase* pB1 = new CDerived( 1, 2 );
CBase* pB2 = new CDerived( 10, 20 );
*pB1 = *pB2;The first argument to the CDerived constructor is assigned to a data member in CBase and the second argument is assigned to a data member in CDerived. I have overloaded operator=() for both CBase and CDerived like this:
CBase& operator=( const CBase& src )
{
m_nBaseData = src.m_nBaseData;
return *this;
}CDerived& operator=( const CDerived& src )
{
m_nDerivedData = src.m_nDerivedData;
return *this;
}When I wrote
*pB1 = *pB2;
(like in the code above), I was expecting both operator=() functions to be called and thus both the CBase data member and the CDerived data member to be copied. However, my pointers being pointers to CBase rather that CDerived, only the CBase::operator=() function was called, resulting in a partial copy of the derived object. I tried making both functions virtual, but the result was the same. The only way I found that resulted in a complete copy is by making my pointers CDerived pointers and adding the following line at the beginning of CDerived::operator=():*(CBase*)this = (const CBase&)src;
Unfortunately, this is not a good solution since it is quite common that I need to store pointers to a base class without knowing exactly what the object is. So, my question is did I miss something somewhere? Is there a way to have objects copy completely with pointers to their base class? Thanks!
-
I'm trying to better understand how operator=() overloading works. I have the following code:
CBase* pB1 = new CDerived( 1, 2 );
CBase* pB2 = new CDerived( 10, 20 );
*pB1 = *pB2;The first argument to the CDerived constructor is assigned to a data member in CBase and the second argument is assigned to a data member in CDerived. I have overloaded operator=() for both CBase and CDerived like this:
CBase& operator=( const CBase& src )
{
m_nBaseData = src.m_nBaseData;
return *this;
}CDerived& operator=( const CDerived& src )
{
m_nDerivedData = src.m_nDerivedData;
return *this;
}When I wrote
*pB1 = *pB2;
(like in the code above), I was expecting both operator=() functions to be called and thus both the CBase data member and the CDerived data member to be copied. However, my pointers being pointers to CBase rather that CDerived, only the CBase::operator=() function was called, resulting in a partial copy of the derived object. I tried making both functions virtual, but the result was the same. The only way I found that resulted in a complete copy is by making my pointers CDerived pointers and adding the following line at the beginning of CDerived::operator=():*(CBase*)this = (const CBase&)src;
Unfortunately, this is not a good solution since it is quite common that I need to store pointers to a base class without knowing exactly what the object is. So, my question is did I miss something somewhere? Is there a way to have objects copy completely with pointers to their base class? Thanks!
You *could* do a <dynamic_cast> in your operator = to see if you have a derived object and make the copy happen. But that's a little tedious and an implimentation nightmare if your class structure will be extended/changed. I'm sure there is a better solution, but it escapes me at the moment. Christian No offense, but I don't really want to encourage the creation of another VB developer. - Larry Antram 22 Oct 2002
C# will attract all comers, where VB is for IT Journalists and managers - Michael P Butler 05-12-2002
It'd probably be fairly easy to make a bot that'd post random stupid VB questions, and nobody would probably ever notice - benjymous - 21-Jan-2003 -
I'm trying to better understand how operator=() overloading works. I have the following code:
CBase* pB1 = new CDerived( 1, 2 );
CBase* pB2 = new CDerived( 10, 20 );
*pB1 = *pB2;The first argument to the CDerived constructor is assigned to a data member in CBase and the second argument is assigned to a data member in CDerived. I have overloaded operator=() for both CBase and CDerived like this:
CBase& operator=( const CBase& src )
{
m_nBaseData = src.m_nBaseData;
return *this;
}CDerived& operator=( const CDerived& src )
{
m_nDerivedData = src.m_nDerivedData;
return *this;
}When I wrote
*pB1 = *pB2;
(like in the code above), I was expecting both operator=() functions to be called and thus both the CBase data member and the CDerived data member to be copied. However, my pointers being pointers to CBase rather that CDerived, only the CBase::operator=() function was called, resulting in a partial copy of the derived object. I tried making both functions virtual, but the result was the same. The only way I found that resulted in a complete copy is by making my pointers CDerived pointers and adding the following line at the beginning of CDerived::operator=():*(CBase*)this = (const CBase&)src;
Unfortunately, this is not a good solution since it is quite common that I need to store pointers to a base class without knowing exactly what the object is. So, my question is did I miss something somewhere? Is there a way to have objects copy completely with pointers to their base class? Thanks!
Assignment operators are not virtual, they are looked up at compile-time. When you hold a pointer to base, pB, and tell the compiler you want to assign something to this base object, as in *pB = whatever; it emits a call to Base::operator=(whatever). On your second problem; from the derived class' operator= call the baseclass' op=, as in: CDerived& operator=( const CDerived& src ) { Base::operator=(src); m_nDerivedData = src.m_nDerivedData; return *this; } Depending on compiler (i.e. MSVC6) you sometimes have to introduce a temporary pointer, like: Base* p = this; *p = src; ... ++luck;
-
I'm trying to better understand how operator=() overloading works. I have the following code:
CBase* pB1 = new CDerived( 1, 2 );
CBase* pB2 = new CDerived( 10, 20 );
*pB1 = *pB2;The first argument to the CDerived constructor is assigned to a data member in CBase and the second argument is assigned to a data member in CDerived. I have overloaded operator=() for both CBase and CDerived like this:
CBase& operator=( const CBase& src )
{
m_nBaseData = src.m_nBaseData;
return *this;
}CDerived& operator=( const CDerived& src )
{
m_nDerivedData = src.m_nDerivedData;
return *this;
}When I wrote
*pB1 = *pB2;
(like in the code above), I was expecting both operator=() functions to be called and thus both the CBase data member and the CDerived data member to be copied. However, my pointers being pointers to CBase rather that CDerived, only the CBase::operator=() function was called, resulting in a partial copy of the derived object. I tried making both functions virtual, but the result was the same. The only way I found that resulted in a complete copy is by making my pointers CDerived pointers and adding the following line at the beginning of CDerived::operator=():*(CBase*)this = (const CBase&)src;
Unfortunately, this is not a good solution since it is quite common that I need to store pointers to a base class without knowing exactly what the object is. So, my question is did I miss something somewhere? Is there a way to have objects copy completely with pointers to their base class? Thanks!
For classes like this, I always create a virtual function named "Copy", the operator= then calls it's open "Copy" function. If the base class has a Copy function, the derived class usually calls it, otherwise it usually calls the base class's operator= function (yes, there are times, albeit rare, I do the copy entirely in the derived class.) (I almost always have a function equivilents to operators, though these functions may incorporate several operators, like "Compare".)