简体   繁体   中英

Should I const_cast “this” when a method only accepts Foo *const?

I have a class Foo which is in a self referencing tree-like structure (minimally):

class Foo {
    public:
        // Gets this child's position relative to it's parent.
        int getPosition() const {
             return parent->indexOf(this);
        }

        int indexOf(const Foo *const child) const {
            return children.indexOf(child); // this line causes an error.
        }
    private:
        Foo *parent;
        QList<Foo *> children;
}

The line return children.indexOf(child) expects const T &value to be passed as per the QList docs , this resolves to Foo *const &value for my scenario.

In order for my getPosition() method to call my own indexOf() method it is required to have a signature of const Foo *child at minimum in order to pass this from a const method. (Since this is const Foo *const ).

My code will not compile however as const Foo *const child cannot be cast to Foo *const child for QList::indexOf . Neither of my methods modify the object state so they should be const (ie I don't want to un-cost getPosition to receive a non-const this ).

So the question is, how do I go from this in a const context ( const Foo *const ) to what QList::indexOf requires. Should I be const casting this inside getPosition since I know that my indexOf (and subsequent calls) will not mutate it?

Is there something else I should have done? Perhaps my design is faulty.

I think this is a perfectly reasonable use case for const_cast , however it's not this you need to const_cast , but child . In this case, QList::indexOf expects a constant pointer to a Foo ( Foo* const ) but child is a constant pointer to a constant Foo ( const Foo* const ). There is no implicit conversion from Foo* const to const Foo* const because that would remove the const-ness from the value being pointed to.

So, to fix your code I would change the line to

return children.indexOf(const_cast<Foo*>(child));

You know QList::indexOf is not going to modify whatever child points to, so this won't produce undefined behavior. I would however add a comment explaining why the const_cast is necessary.

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM