Value of a pointer to base type when assigned to a derived type

V

Vijai Kalyan

A very simple question. I have never had occasion to think about this
before.

Consider the following:

class A
{
virtual unsigned long bar()
{
return reinterpret_cast<unsigned long> (this);
}
};

class B
{
};

void foo()
{
B* b = new B;
A* a = b;
std::cout << "b == a?" << std::boolalpha << (a == b) << std::endl;
}

I would have thought this would print

true

but it doesn't. Does this mean that "a" only points at the "A" part of
"b"?

But, of course, if I do "a->bar()" the correct function from "B" will
be invoked. This is due to the fact that bar is a virtual function
which means the compiler does the correct thing.

Can someone tell me then why the pointers are different?

thanks,

-vijai.
 
M

Mike Wahler

Vijai Kalyan said:
A very simple question. I have never had occasion to think about this
before.

Consider the following:

class A
{
virtual unsigned long bar()
{
return reinterpret_cast<unsigned long> (this);

Why are you trying to convert a pointer to an unsigned long?
What would that mean? (If it has any meaning at all, it will
be platform specific, not specified by the language).
}
};

class B
{
};

void foo()
{
B* b = new B;
A* a = b;

This is not valid, and a compiler should give an error.
There's no defined conversion from type 'B*' to type 'A*'
std::cout << "b == a?" << std::boolalpha << (a == b) << std::endl;

Same problem here with the expression 'a == b'.
}

I would have thought this would print

true

I wouldn't. I would not expect the code to compile.
but it doesn't. Does this mean that "a" only points at the "A" part of
"b"?

'b' is not part of 'a'. They're completely different, unrelated
types.
But, of course, if I do "a->bar()" the correct function from "B" will
be invoked.

No. 'B' has no member functions. And even if it did, calling an
'A' member function has nothing to do with 'B'. Why do
you think it does?
This is due to the fact that bar is a virtual function
which means the compiler does the correct thing.

The fact that 'bar()' is virtual is irrelevant. 'B' is not
derived from 'A'. It's a completely different, unrelated type.
Can someone tell me then why the pointers are different?

As soon as you post some compilable, valid code, we
can discuss how it should behave.

-Mike
 
V

Vijai Kalyan

Sorry,

class B : public virtual A
{
};

And no, there is no meaning to convert the value of (this) to unsigned
long. It just is for the sake of putting something in the constructor.

-vijai.
 
J

Jim Langston

Vijai Kalyan said:
Sorry,

class B : public virtual A
{
};

And no, there is no meaning to convert the value of (this) to unsigned
long. It just is for the sake of putting something in the constructor.

-vijai.

Under Microsoft Visual C++ .net 2003 it returns:
b == a?true

with a compile warning:
'reinterpret_cast' : pointer truncation from 'A *const ' to 'unsigned long'

Code is:

#include<iostream>
class A
{
virtual unsigned long bar()
{
return reinterpret_cast<unsigned long> (this);
}
};
class B: public virtual A
{
};
void foo()
{
B* b = new B;
A* a = b;
std::cout << "b == a?" << std::boolalpha << (a == b) << std::endl;
}

int main()
{
foo();
char x;
std::cin >> x;
return 0;
}
 

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

Forum statistics

Threads
473,766
Messages
2,569,569
Members
45,042
Latest member
icassiem

Latest Threads

Top