On 08/09/2014 06:01, Danny Yoo wrote:
@property
def _avatar(self):
return self._avatar
Hi Joel,
The above code looks strange to me. The method and the field name
should not use the same name.
ah! good catch Danny. I didn't write it, I was commenting on the OP code.
But (and maybe this was discussed earlier in the thread), what value
is using the property decorator instead of just saving the data to
attributes?
Let's first point to documentation that says what "property" is:
https://docs.python.org/2/library/functions.html#property
If you read it a bit, one of the key terms that should come up is
"managed attribute".
What do they mean by this?
A managed attribute is an attribute that the class's definition
actively controls.
Let's use a concrete example: say that we'd like to make sure a
Person's name is always capitalized. We might try to enforce this
capitalization property in the constructor.
###############################
class Person(object):
def __init__(self, name):
self.name = name.title()
def greet(self):
print("Hi, I'm %s" % self.name)
p = Person("joel goldstick")
p.greet()
###############################
However, this does not stop clients from assigning directly to the name,
#####################
p.name = "joel goldstick"
#####################
and therefore breaking a desire to keep the name capitalized. So this
might be a problem.
So what we'd like is the following: to make sure that there's some
kind of program logic that kicks in whenever we assign to Person.name.
In some programming languages, we do this by marking the attribute
name in some way that makes it clear not to access it directly, and we
provide "setter" and "getter" methods, the code that can "manage" this
attribute.
#############################
class Person(object):
def __init__(self, name):
self._name = name.title()
def getName(self):
return self._name
def setName(self, name):
self._name = name.title()
def greet(self):
print("Hi, I'm %s" % self._name)
## client code:
p = Person("joel goldstick")
print(p.getName())
p.greet()
p.setName("juan christian")
print(p.getName())
p.greet()
#############################
Python allows us to get "setter" and "getter"-like behavior while
still allowing client code to use the attribute with what looks like
direct attribute access:
#################################
class Person(object):
def __init__(self, name):
self._name = name.title()
@property
def name(self):
return self._name
@name.setter
def name(self, newName):
self._name = newName.title()
def greet(self):
print("Hi, I'm %s" % self._name)
## client code:
p = Person("joel goldstick")
print(p.name)
p.greet()
p.name= "juan christian"
print(p.name)
p.greet()
#################################
where now the client code looks simpler, but the class definition
still gets to manage the attribute's value.
Hopefully that helps to make the suggestions in this thread a little
more understandable in context. Python's properties allow us to make
the client code look direct but still allow for attribute management.
_______________________________________________
Tutor maillist - Tutor@python.org
To unsubscribe or change subscription options:
https://mail.python.org/mailman/listinfo/tutor
I was taught to [generally] always use getter and setter, and I have
found this clear and useful. But I am a beginner, so my question is
whether there there are any other reasons to use the methods outlined
above by the always helpful Danny Yoo, in addition to the simplification
to which he draws attention?
--
Sydney Shall
_______________________________________________
Tutor maillist - Tutor@python.org
To unsubscribe or change subscription options:
https://mail.python.org/mailman/listinfo/tutor