Jump to content
  • Advertisement
Sign in to follow this  

[C++] Scott Meyers's item 22 - private data members

This topic is 2861 days old which is more than the 365 day threshold we allow for new replies. Please post a new topic.

If you intended to correct an error in the post then please contact us.

Recommended Posts

Most of the time Meyers writing style is clear and concise, but this item has befuddled me.

He basically states:
Never, ever, use protected data members

and goes on saying that protected data members are as 'un'capsulated as public members and so on...

My question is: how will my derived classes be able to modify its (base) members values then?

I know that a virtual function overridden in the derived class can access its base members, but until now I've been declaring all those base members as protected, whenever I want to change them through the derived class... Now, if they are private to the base class, how will my derived class be able to change it?

is it something to do with the way I inherit the base class?

like using class Derived : public Base {} ?

thanks!

Share this post


Link to post
Share on other sites
Advertisement
I believe his logic is to have getters and setters defined in the base class (which those functions could be declared protected if you wish), so the base class always defines the control over it's members.

Share this post


Link to post
Share on other sites
Quote:
My question is: how will my derived classes be able to modify its (base) members values then?
Your derived classes can interact with the base class in the same way that non-derived classes do - through the presented interface. You should need to use protected about as often as you use friend -- to punch a sneaky back-door through your safe/sanity-checked interface.

The fact that you're asking that question indicates that your base class does not provide a full and complete abstraction - some details of it's inner workings are un-implemented, which makes the class harder to be proven to be correct. Often this means that the base class exists only to facilitate code-re-use (via inheriting this common code into the derived classes), which is often better achieved via composition instead.
Quote:
Original post by Rattrap
I believe his logic is to have getters and setters defined in the base class (which those functions could be declared protected if you wish), so the base class always defines the control over it's members.
That's better than nothing, but if you've got a class that provides direct access to it's members via set/get methods, then it's sometimes an indication that the class is not a very good abstraction of whatever problem it's designed to solve.

Share this post


Link to post
Share on other sites
Quote:
Original post by Hodgman
Quote:
My question is: how will my derived classes be able to modify its (base) members values then?
The fact that you're asking that question shows that your base class does not provide a full and complete abstraction.

Your derived classes can interact with the base class in the same way that non-derived classes do - through the presented interface. You should need to use protected about as often as you use friend -- to punch a sneaky back-door through your safe/sanity-checked interface.


ooookays. but how do I accomplish this? by using getters & setters in the base class?

Share this post


Link to post
Share on other sites
Quote:
Original post by Hodgman
Without knowing what your problem is, I would guess that the answer is "don't use inheritance"...


It is no really a problem in my code/project. I'm trying to understand why Meyers proposes something, not using protected members, but does not offer an example of the "right way" to do it. Maybe he does in another item, but I couldn't find it yet :)

And then, it was so natural for me the use of protected data members ( I usually work with no more than 1 level of inheritance) that stroke me as odd that using it was bad design.

Share this post


Link to post
Share on other sites
The first thing that pops to my mind is that direct access to the variable would be scattered around the code. Not only that but if someone else than you derives your class, and have direct access to your variable you are not even in control of when, where and how this variable are accessed.
Using getter/setter functions will make sure direct access happens at one and only one place in the code, and any changes to how the getter/setter functions access the variable will affect all clients immediately.
Not sure if that is what Meyers had in mind but its a pretty good reason in itself I would say.

Share this post


Link to post
Share on other sites
I think I see what he meant.

at the very first pages he says something about programming "to a library" (can't remember the exact words), but it was something on the way of "think as if people will use your code to complement/enhance theirs".

And yes, now I see that having protected variables running around some code that I am don't even aware of can for sure damage many things whenever I a change to the base class is needed.

Share this post


Link to post
Share on other sites
Quote:
Original post by pulpfist

Using getter/setter functions will make sure direct access happens at one and only one place in the code, and any changes to how the getter/setter functions access the variable will affect all clients immediately.

Getters and setters are the same as just making variables public. It even saves typing.

Getters/setters became so popular because of deficiencies of Java as a language when tackling its most common problem - ORM. And since Java is a language just about everyone must learn, they became the magic bullet to everything.


struct FooBar {
void moveTo(int x,int y);
void jump();
void climb();
void render(Canvas & c) {
c.draw_rect(this->x, this->y, this->width, this->height);
}
}
There, no need for any accessors or such. That is what OO should aspire to. Note that no variables whatsoever are visible, everything else is public. Any class extending this cannot break the underlying class, nor does it depend on non-public specifics.

It is not always a silver bullet though, sometimes it's practical to violate some of these principles. And some types of functionality are simply too trivial to OO-ify, such as geometries (rect, point, ...), or trivial value types (name/value pairs, strings, ...).

Don't go OO crazy with Point or Rect class. Reserve it for complex objects and actions that express a lot of logic via simple interface.

Share this post


Link to post
Share on other sites
Think about the reason you would make any data member non-public: there's a class invariant that you want to maintain. If the variable is private then only the member functions of that class are responsible for maintaining the class invariant. If the variable is protected then not only are the member functions of the class responsible for maintaining the invariant, but all of the member functions of all the derived classes become responsible for maintaining the class invariant. This is generally a sub-optimal way of managing things.

Share this post


Link to post
Share on other sites
Sign in to follow this  

  • Advertisement
×

Important Information

By using GameDev.net, you agree to our community Guidelines, Terms of Use, and Privacy Policy.

Participate in the game development conversation and more when you create an account on GameDev.net!

Sign me up!