parallel
parallel

Reputation: 111

cast Derived*const to Base*const

Edit - Put the question into context a bit more.

Given:

struct Base
{
    ...
};
struct Derived : public Base
{
    ...
};
class Alice
{
    Alice(Base *const _a);
    ...
};
class Bob : public Alice
{
    Bob(Derived *const _a);
    ...
};

When I try to implement

Bob::Bob(Derived *const _d) : Alice(static_cast<Base*const>(_d)) { }

it does not work. a const_cast doesn't make sense to me as I don't want to change the constness, and I'm not changing what I'm pointing to, so why then does g++ tell me

invalid static_cast from type ‘Derived* const’ to type ‘Base* const’

? If I leave out the cast, it says

no matching function for call to ‘Alice::Alice(Derived* const)’

If anyone could shed any light on this It'd be much appreciated.

Upvotes: 5

Views: 3730

Answers (7)

Tomek
Tomek

Reputation: 4659

While I am not sure (too little context) I think you might have meant Base const * and Derived const *.

Base const * is a pointer to constant Base object. Base * const is a constant pointer to modifiable Base object.

Upvotes: 0

AnT stands with Russia
AnT stands with Russia

Reputation: 320521

The only problem here is that Alice::Alice is private in Alice. Bob has no access to Alice::Alice.

There are no problems with the cast whatsoever. In fact, you don't need a static_cast for it. It should be converted implicitly.

The static_cast you currently have is valid, except for a redundant const qualifier in the target type. That const there simply makes no sense, but it is not an error.

Why your compiler is issuing these bizarre error messages is not clear to me. I suspect that the code you posted is fake.

Upvotes: 0

Kiril Kirov
Kiril Kirov

Reputation: 38173

This compiles perfectly on g++ 4.4.3, no even warnings:

#include <iostream>

struct Base
{
    Base()
    {
    }
};

struct Derived : public Base
{
    Derived() {}
};

class Alice
{
public:
    Alice( Base *const _a )
    {
        std::cout << "Alice::Alice" << std::endl;
    }
};

class Bob : public Alice
{
public:
    Bob(Derived *const _a) 
        : Alice( static_cast< Base * const >( _a ) )
    {
        std::cout << "Bob::Bob" << std::endl;
    }
};

int main()
{
    Derived* pDer = new Derived();
    Bob b( pDer );
    return 0;
}

Upvotes: 1

parallel
parallel

Reputation: 111

The problem was that Derived was an incomplete type, i.e. forward declared. I'm afraid I've been giving everyone a hard time :( The answer popped up when Kiril Kirow proposed using a dynamic-cast, upon which g++ spat out this slightly more helpful error:

error: cannot dynamic_cast ‘_d’ (of type ‘struct Derived* const’) to type ‘struct Base* const’ (source is a pointer to incomplete type)

Unfortunately, I had forward declared Derived, but I hadn't realized it was relevant, and it was hidden several headers further down, which would have had me posting too much code here. Sorry everyone, but I hope this at least helps somebody else later.

Upvotes: 6

Cheers and hth. - Alf
Cheers and hth. - Alf

Reputation: 145279

You have unrelated types Alice and Base. Change the Alice constructor to take a Base*.

By the way, I suspect that you have your const placements wrong.

Cheers & hth.,

Upvotes: 0

Armen Tsirunyan
Armen Tsirunyan

Reputation: 133014

I have a theory. What if during derivation you had accidentally forgotten to specify that the derivation is public? In this case it would be private by default and the above conversion would be inaccessible.

Are you sure you wrote

class Derived : ***public*** Base {...}

?
Or maybe you forgot public? Just a theory...

Upvotes: 1

Oliver Charlesworth
Oliver Charlesworth

Reputation: 272517

You don't need any cast at all. You have const pointers, not pointers to const objects. And it's legal to assign the address of a derived object to a pointer-to-base without a cast.

Upvotes: 1

Related Questions