Take the 2-minute tour ×
Programmers Stack Exchange is a question and answer site for professional programmers interested in conceptual questions about software development. It's 100% free, no registration required.

In C++ I was told that my classes shouldn't have getters and setters: Doing it wrong... blog post.

On the other hand, in Objective-C, the direct use of ivar is discouraged, because the getters allow to do lazy instantiation, and setters make KVO easy.

Why is that difference?

share|improve this question
1  
I don't think that blog post is saying you should directly access class members rather than using getters and setters.. it is saying that you should do neither, and instead encapsulate functionality in proper OO methods. –  Carson63000 Mar 3 '13 at 10:23
    
@Carson63000 So IIUC getters and setters are recommended as long as it is for internal use, and no OO design should expose (too much, if any) internal state. –  grasGendarme Mar 3 '13 at 10:47
add comment

3 Answers

up vote 7 down vote accepted

I think the best takeaway from the "Doing it wrong..." post is that exposing public accessors without a good reason breaks encapsulation by giving external classes the ability to modify and inspect state that ought not be made public. It's just expressed in an absolutist fashion (I'd argue if you have a Contact object, and want to put that contact's name on a label for an address book application, at some point Contact will probably have to expose its name to another object). Regardless, no matter what the language, making accessors available without thought is going to break encapsulation and lead to tight coupling.

This is orthogonal to the best practice in Objective-C of using accessors for all (at least most) instance variable access. No where does Objective-C recommend making all your accessors publicly visible. Often you will have a class extension visible only to the class's own implementation that defines most of its instance variables and then the class's own implementation uses the accessors. And certainly, external code should always use the accessors - but they still should only be made visible to external code if absolutely necessary.

share|improve this answer
    
You also use properties in Objective-C for key value coding so you can access/set values based on a string such as @"foo.bar". There's really no equivalent in C++ for key-value coding, except for maybe over-riding "[]" or "()" to take a name and return a value. As a rule of thumb, you should think first about hiding the implementation (i.e. how the data is represented vs how it's stored) rather than allowing people to reach into your objects. –  ipaul Mar 3 '13 at 16:00
    
+1 for "without good reason." There's always rare exceptions that aren't necessarily awful. –  Erik Reppen Mar 5 '13 at 4:05
    
@ipaul good point, we should always be striving to keep our public interfaces free of implementation details. KVC works fine without properties however, and the Objective-C runtime can go even further. So avoiding having properties in a private interface won't really do you any good, if that's what you're suggesting. Objective-C information hiding is in many ways more of a voluntary agreement, rather than the law :) –  Carl Veazey Mar 5 '13 at 5:10
    
@ErikReppen thank you. I think if you're going to program with a Model-View-Controller architecture it's tough to avoid having model objects that expose information needed by the controller to populate the view. The author's comments on his post indicate he's not satisfied with MVC, however, so I'm sure his thoughts have to be taken in that context - if you're working in a framework that's not MVC then you might have more luxury in avoiding objects keeping hold of state, I don't know. –  Carl Veazey Mar 5 '13 at 5:14
    
I write JS. It's okay in JS for some things to not be objects. I think it helps us see the benefit of OOP better TBH. –  Erik Reppen Mar 5 '13 at 5:35
show 2 more comments

Setters and getters are the technology that came from visual basic properties in 1980's. Since they're often used together with the programming techniques that also come from same place, it's considered bad practise. Problem with getters and setters is that the behaviour of the class gets moved to the user of the class, and class no longer handles it's own behaviour; but supports any behaviour possible. This does not create a good class, since it's not doing the decisions that are normally part of class' responsibility.

share|improve this answer
add comment

As a C# developer, I use getters/setters all the time. Since I rarely (but still do) use C++, I might could offer a different perspective on this one.

To my eye, the bulk of difference of acceptability between C++ and C# has been due to conventions between users of a language (though there are others I'll get to later...). Most of the time in C++, I just don't need to use a getter/setter because it is not encouraged to do so. Unlike the blog post, I don't even view it as a matter of 'right way to code' or 'wrong way to code.' It's a convention that allows other humans to make heads or tails of what I've written/maintained.

C# does not mitigate that need, and as far as I've seen, there's no evidence to say that getters/setters in C# are any more or less peformant than methods in C++ (I would assume they're on roughly the same order, but that's a gut feeling, there.) Yet, the general feeling in the C# community is that, while methods are preferable, properties are great for taking methods like:

public string GetName()
{
    return _lastName + ", " + _firstName + " " + _middleInitial;
}

public string SetName(string fullName)
{
    // Assumptions are made here; this is just example code!
    string[] frags = fullName.Split(' ');
    _firstName = frags[0];
    _middleName = frags[1];
    _lastName = frags[2];
}

and creating a slightly 'shorter', different, but reasonably readable syntax like:

public string Name
{
    get { return _lastName + ", " + _firstName + " " + _middleInitial; }
    private set 
    {
        string[] frags = value.Split(' ');
        _firstName = frags[0];
        _middleName = frags[1];
        _lastName = frags[2];
    }
}

You could say that to a C# or Java programmer, we view properties as syntactic sugar for simple methods, since that's all a getter/setter really is: a method.

Another wrinkle in the technologies lies in various frameworks. For instance, in my current shop, our MVC projects are set up such that we're more or less required to use getters and setters by NHibernate and the MVC framework itself. We've had conversations about the perceived overabundance of properties in our app, but in the end we had no technical recourse to revise those to simple methods. We have to use properties because reflection is used to retrieve properties, and thus their contents. Our code would be bigger and nastier without them, so no one really complains all that much.

To finally answer your question, though, I think that dives to the heart of the matter.

A C++ programmer expects to need the deep technical details of a given operation; instead of obscuring this machination with syntactic sugar, it's more understandable to just bite the bullet and do the work. It's not that C++ programmers are averse to syntactic sugar at all (in fact, I find myself yearning for better ways to express my C++ code when I use it...), but the things you turn to C++ for and the things you use properties for typically don't mesh well on a practical level*.

A C# or Java programmer is taking advantage of the virtual machine interposed between the physical layer and our high-level code; we lose little by utilizing the syntactic sugar, and in return gain (slightly) improved readability without wholly violating encapsulation...providing the getters/setters are implemented correctly. The things you turn to C# or Java for do mesh well with properties on a practical level.

*: Note that I'm not a frequent C++ user! I beg for correction, if anyone has any to give.

share|improve this answer
    
Dictionaries, structs, anonymous objects... Doesn't C# basically have all the alternatives? Without paying attention to who owns the data it's just C with functions tied to a namespace to me. You're still just following method calls. –  Erik Reppen Mar 5 '13 at 4:15
add comment

Your Answer

 
discard

By posting your answer, you agree to the privacy policy and terms of service.

Not the answer you're looking for? Browse other questions tagged or ask your own question.