Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

public const doesn't override private const function?

I have a class with a header like this:

public:
    const dtMeshTile* getTile(int i) const;

private:
    dtMeshTile* getTile(int i);

When I try to use it like this:

const dtMeshTile* const tile = navmesh->getTile(i);

I'm getting a "'dtMeshTile* getTile(int)' is private within this context" How can I specify the public function?

like image 896
mpellegr Avatar asked Jun 12 '13 14:06

mpellegr


People also ask

Can you override a const function?

const is part of the signature, and leaving it off changes the signature, and thus hides the method rather than overrides it. "

Can constructor be const in c++?

Constructors may be declared as inline , explicit , friend , or constexpr . A constructor can initialize an object that has been declared as const , volatile or const volatile . The object becomes const after the constructor completes.


2 Answers

Consider:

#include <cstdlib>

class Bar {}; 
class Foo 
{
public:
    Foo (Bar& bar)
    :   
        mBar (bar)
    {   
    }   
    const Bar& get() const
    {   
        return mBar;
    }   
private:
    Bar& get()
    {   
        return mBar;
    }   

    Bar& mBar;
};

int main()
{
    Bar bar;
    Foo foo (bar);
    Bar& ref = foo.get();
}

At the point of the call: const Bar& ref = foo.get(); you might expect the const version of get() to be called, because you are assigning a const reference.

But this is not the case. Return types are not a part of a function's (or method's) signature, so when the compiler is looking for which function to call in a list of possible overloads, the return type is not considered. (In fact, the Standard rejects function overloads which differ only by return type.)

So, how does the compiler decide which function to call? By looking at the information is does have available to it. The tweo overloads are identical in terms of parameters (both are void), so the only thing it has to go on is the static type of the object used to make the call: foo. That static type in this case is Foo -- decidedly non-const.

Therefore it tried to call the only function it can: the non-const version of get(). Which of course won't compile because that is private.

In order to fox this, the static type can be changed to be a const Foo (or something similar), like this:

Foo foo (bar);
Bar& ref = foo.get();

Or maybe...

Foo foo (bar);
const Bar& ref = static_cast <const Foo&> (foo).get();

But in practice, I would rather advise that the names of these functions be unambigious, rather that relying on such "tricks" to contort the compiler in to doing what you want.

like image 190
John Dibling Avatar answered Sep 29 '22 06:09

John Dibling


make sure navmesh is const in the context of your call. But I would not recommend const_cast it, you might read this http://www.parashift.com/c++-faq/overview-const.html .

like image 40
Slava Avatar answered Sep 29 '22 06:09

Slava