Adding a const qualifier to a member function

c++, c++11, template-meta-programming, templates, type-traits

Solution

This seems easiest to do with a specialization:

template< bool isConst >
struct Interface;

template <>
struct Interface<false>
{
    TypeA& GetXpo3Container()
    {
        return config_.type_a_member_;
    }
};

template <>
struct Interface<true>
{
    const TypeA& GetXpo3Container() const
    {
        return config_.type_a_member_;
    }
};

Edit: although I'm not entirely sure what this adds. Wouldn't it be easier to have

struct Interface
{
    TypeA::type& GetXpo3Container()
    {
        return config_.type_a_member_;
    }
    const TypeA::type& GetXpo3Container() const
    {
        return config_.type_a_member_;
    }
};

and use `const Interface` where appropriate? Or is this not an option for some other reason?

Edit 2: my `std::enable_if` use was wrong, it's gone now.

Problem

I am currently writing an interface class that should provide access to to internal elements of a complex structure as const or non-const references. The idea is that some modules are granted const access and some modules are granted full access. I have used the 'type_traits' 'std::add_const' to conditionally qualify the return type of the internal member functions, unfortunately I cannot think of a way of conditionally qualifiying the member functions as const or non-const. Is this even possible? if so how? E.G: ``` template< typename T, bool isConst > struct apply_const { typedef T type; }; template<typename T> struct apply_const<T, true> { typedef typename std::add_const<T>::type type; }; template< bool isConst > const Interface { /// @brief get the TypeA member typename apply_const<TypeA, isConst >::type& GetXpo3Container() // how do I conditionally add a const qualifier { return config_.type_a_member_; } typename apply_const<Profile, isConst >::type& GetProfile( unint32_t id ) // qualifier ??? { return config_.profiles.get( id ); } // .... lots more access functions ConfigType config_; // the config }; ``` Note: the underlying reason for separating / creating 2 versions of the interface is that they will be providing access to different instances of `config` - one which is writable and one which is not. The sub-system being developed is an embedded Netconf Agent, which supports `<running>` and `<candidate>` configurations.

Original source