virtual assignment operator/polymorphism question

S

Stephan Kurpjuweit

Hi,

could you please help me with the following example?


struct Base
{
virtual Base& operator = (const Base &k) {}
};

struct Derived: public Base
{
// 1
virtual Derived& operator = (const Derived &k) {}

// 2
virtual Base& operator = (const Base &k) {}
};

int main(int argc, char* argv[])
{
Derived *dp = new Derived();
Base *bp = new Derived(*dp);

*bp = *dp;

return 0;
}


Why does the assignment in main lead to a call to the second assignment
operator (// 2) and not to the first one (//1)?

Thank you,
Stephan
 
V

Victor Bazarov

Stephan said:
Hi,

could you please help me with the following example?


struct Base
{
virtual Base& operator = (const Base &k) {}
};

struct Derived: public Base
{
// 1
virtual Derived& operator = (const Derived &k) {}

// 2
virtual Base& operator = (const Base &k) {}
};

int main(int argc, char* argv[])
{
Derived *dp = new Derived();
Base *bp = new Derived(*dp);

*bp = *dp;

return 0;
}


Why does the assignment in main lead to a call to the second assignment
operator (// 2) and not to the first one (//1)?

Because // 1 does not override the assignment operator in Base, but the
// 2 does.

V
 
J

John Harrison

Stephan Kurpjuweit said:
Hi,

could you please help me with the following example?


struct Base
{
virtual Base& operator = (const Base &k) {}
};

struct Derived: public Base
{
// 1
virtual Derived& operator = (const Derived &k) {}

// 2
virtual Base& operator = (const Base &k) {}
};

int main(int argc, char* argv[])
{
Derived *dp = new Derived();
Base *bp = new Derived(*dp);

*bp = *dp;

return 0;
}


Why does the assignment in main lead to a call to the second assignment
operator (// 2) and not to the first one (//1)?

1) *bp is of static type Base, so the compiler generates a virtual call to
Base::eek:perator=(const Base&).

2) At run-time the dynamic type of *bp is examined, since that is Derived
the actual function that gets called is the overridden version in the
Derived class, i.e. Derived::eek:perator=(const Base&)

Derived::eek:perator=(const Derived&) never gets considered at step 1 because
there is no similar function in the Base class, so it cannot be called at
step 2.

john
 
A

Andrey Tarasevich

Stephan said:
Hi,

could you please help me with the following example?


struct Base
{
virtual Base& operator = (const Base &k) {}
};

struct Derived: public Base
{
// 1
virtual Derived& operator = (const Derived &k) {}

// 2
virtual Base& operator = (const Base &k) {}
};

int main(int argc, char* argv[])
{
Derived *dp = new Derived();
Base *bp = new Derived(*dp);

*bp = *dp;

return 0;
}


Why does the assignment in main lead to a call to the second assignment
operator (// 2) and not to the first one (//1)?
...

Because selection of candidate functions for overload resolution is
based on _static_ type of the object. In this case static type of
left-hand side of the assignment is 'Base'. This means that only
'Base::eek:perator=(const Base&)' is considered (and, therefore, chosen) by
overload resolution.

Now, since 'Base::eek:perator=(const Base&)' is declared as 'virtual', the
choice of actual function to call will be based on _dynamic_ type of the
object. In this case dynamic type of left-hand side of the assignment is
'Derived', which means that 'Derived::eek:perator=(const Base&)' will be
called.
 

Ask a Question

Want to reply to this thread or ask your own question?

You'll need to choose a username for the site, which only take a couple of moments. After that, you can post your question and our members will help you out.

Ask a Question

Members online

No members online now.

Forum statistics

Threads
473,995
Messages
2,570,230
Members
46,819
Latest member
masterdaster

Latest Threads

Top