0

I am exploring decorators in Python, and as a person who came to Python from other languages, I am a bit confused about the purpose of @property and its @xxx.setter brother. In Java and C++ get_xxx() and set_xxx() are usually the way to organize encapsulation. In Python we have these two decorators, which require specific syntax, and name matching in order to work. How is @property better than get-set methods?

I have checked this post and still, what are the advantages of @property besides the availability of the += operator?

Oleksandr Novik
  • 489
  • 9
  • 24
  • 4
    The point is **you shouldn't write getters and setters in Python**. This is *the key thing to understand*. Just use normal `self.x = whatever`. – juanpa.arrivillaga Dec 14 '21 at 19:32
  • The *advantage* of using `property` is that you **dont' have to write boilerplate getters and setters**. You just use plain attributes, and *if and when* you require controlling access to the attribute, **only then** do you add a property, and you don't break the interface for clients to your class, or your own implementation. So you get *encapsulation without boilerplate getters and setters* – juanpa.arrivillaga Dec 14 '21 at 19:33
  • 1
    See [this answer to a related question I wrote a while back](https://stackoverflow.com/a/43266014/5014455) – juanpa.arrivillaga Dec 14 '21 at 19:35
  • "which require specific syntax, and name matching in order to work." They don't actually, although, it will if you use the `@` syntax, but that isn't required. – juanpa.arrivillaga Dec 14 '21 at 19:36
  • 1
    @juanpa.arrivillaga thanks, the link to your answer provided me with all the info I needed. – Oleksandr Novik Dec 14 '21 at 19:38

1 Answers1

2

The best part of using property for an attribute is that you don't need it.

The philosophy in Python is that classes attributes and methods are all public, but by convention - when you prefix their name with a single "_"

The mechanism behing "property", the descriptor protocol, allows one to change a previous dumb plain attribute into an instrumented attribute, guarded with code for the getter and setter, if the system evolves to a situation where it is needed.

But by default, a name attribute in a class, is just a plain attribute. You do person.name = "Name"- no guards needed, no setting method needed nor recommended. When and if it one needs a guard for that (say, to capitalize the name, or filter on improper words), whatever code uses that attribute needs no change: with the use of property, attribute assignment still takes place with the "=" operator.

Other than that, if using "=" does not look prettier than person.set_name("Name") for you, I think it does for most people. Of course, that is subjective.

jsbueno
  • 99,910
  • 10
  • 151
  • 209