c++castingconstants

Cast a list of pointers to a list of constant pointers in C++


I have a class that needs to build / maintain a list of pointers to objects, but then should return a constant list to constant pointers to the same data. So something like:

class Foo {
private:
   std::list<Word *>  myList;
public:
   const std::list<const Word *>  getList() { return myList; }
}

But if I compile that, I get an error:

error: cannot convert 'const std::__cxx11::list<Word*>*' to 'const std::__cxx11::list<const Word*>*' in return

Is there a way to cast a list of pointers to a list of constant pointers?


Solution

  • Is there a way to cast a list of pointers to a list of constant pointers?

    As literally asked, no. list<T*> and list<T const *> are not similar in the same way that T* and T const* are similar.

    If you can generalize to just returning something iterable (and you're using reasonably up-to-date C++) you can avoid copying the whole list like so:

    auto getList() const
    {
        return myList | std::views::transform(
            [](int *p) { return const_cast<int const *>(p); }
        );
    }
    

    Otherwise the usual solution is to hold almost anything in your list apart from raw pointers.

    Anything with const-qualified methods that correctly propogate constness from a const iterator through to the final object will be fine - there are some examples on this rather elderly question, or you can find implementations of the std::experimental::propagate_const.