Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Why provide two get functions

Tags:

c++

boost

class T
{};

class AccessT
{
public:
    boost::shared_ptr<const T> getT() const {return m_T;}
    boost::shared_ptr<T>       getT()       {return m_T;}

private:
    boost::shared_ptr<T> m_T;
};

Question> I saw lots of similar codes as above in the legacy project. I really don't understand the point of doing so. Why not just simply provide the following instead:

class T
{};

class AccessTModified
{
public:
    boost::shared_ptr<T> getT() const { return m_T; }

private:
    boost::shared_ptr<T> m_T;
};

The initial argument may be that boost::shared_ptr<const T> getT() const will not let const object modifies the T by accident. If that is the case, is it a practice that all such functions should provide two versions? To me, I feel very tedious!

like image 968
q0987 Avatar asked Feb 14 '13 17:02

q0987


2 Answers

You are correct: the purpose of boost::shared_ptr<const T> getT() const is to ensure that const objects can't modify the T by accident.

In C++, this is known as const correctness and is usually considered to be good C++ design. As you said, it often results in getters having two versions (a const and a non-const version). It can be initially tedious (although it's not bad once you get used to it), but the results can be quite useful. Const correctness lets you declare functions like

void DoSomething(const AccessT& item);

that promise not to modify item so that the compiler throws an error if DoSomething does anything that's declared as possibly modifying item.

Although const correctness is usually considered to be good C++ design, some developers decide that the overhead of having to declare const and non-const versions of some functions to be more trouble than it's worth.

The C++ FAQ has a whole section on const correctness, if you're interested in more information.

like image 143
Josh Kelley Avatar answered Oct 04 '22 07:10

Josh Kelley


This pattern is common when the need for an accessor class is felt, but the author doesn't want to go the whole way of defining AccessT and AccessTconst for access and constant access. The hack you see is the less tedious way of making constant and non-constant access possible through constant and non-constant accessors.

The advantage of this pattern is an easy implementation, the disadvantage is that you mingle the concepts of "const pointer" and "pointer to const". If an AccessT provides a setT member, confusion about const-ness will ensue.

You can contrast this access pattern with the const_ pattern shown e.g. by iterators, which come as const_iterator and iterator and allow all four combinations of changeable iterator and changeable iterated.

like image 30
thiton Avatar answered Oct 04 '22 05:10

thiton