与经典的getter+setter相比,@property表示法有什么优点?在哪些特定的情况下,程序员应该选择使用其中一种而不是另一种?

属性:

class MyClass(object):
    @property
    def my_attr(self):
        return self._my_attr

    @my_attr.setter
    def my_attr(self, value):
        self._my_attr = value

没有属性:

class MyClass(object):
    def get_my_attr(self):
        return self._my_attr

    def set_my_attr(self, value):
        self._my_attr = value

当前回答

在复杂的项目中,我更喜欢使用带有显式setter函数的只读属性(或getter):

class MyClass(object):
...        
@property
def my_attr(self):
    ...

def set_my_attr(self, value):
    ...

在长期存在的项目中,调试和重构比编写代码本身花费更多的时间。使用@property有几个缺点。Setter,使调试更加困难:

1) python允许为现有对象创建新属性。这使得下面的打印错误很难追踪:

my_object.my_atttr = 4.

如果你的目标是一个复杂的算法,那么你将花费相当多的时间试图找出它不收敛的原因(注意上面一行中额外的“t”)

2) setter有时可能演变成一个复杂而缓慢的方法(例如击中数据库)。对于另一个开发人员来说,很难弄清楚为什么下面的函数非常慢。他可能会花很多时间分析do_something()方法,而my_object。My_attr = 4。其实是减速的原因:

def slow_function(my_object):
    my_object.my_attr = 4.
    my_object.do_something()

其他回答

在复杂的项目中,我更喜欢使用带有显式setter函数的只读属性(或getter):

class MyClass(object):
...        
@property
def my_attr(self):
    ...

def set_my_attr(self, value):
    ...

在长期存在的项目中,调试和重构比编写代码本身花费更多的时间。使用@property有几个缺点。Setter,使调试更加困难:

1) python允许为现有对象创建新属性。这使得下面的打印错误很难追踪:

my_object.my_atttr = 4.

如果你的目标是一个复杂的算法,那么你将花费相当多的时间试图找出它不收敛的原因(注意上面一行中额外的“t”)

2) setter有时可能演变成一个复杂而缓慢的方法(例如击中数据库)。对于另一个开发人员来说,很难弄清楚为什么下面的函数非常慢。他可能会花很多时间分析do_something()方法,而my_object。My_attr = 4。其实是减速的原因:

def slow_function(my_object):
    my_object.my_attr = 4.
    my_object.do_something()

简单的答案是:properties轻松获胜。总是这样。

有时需要getter和setter,但即使这样,我也会将它们“隐藏”到外部世界。在Python中有很多方法可以做到这一点(getattr, setattr, __getattribute__,等等…,但最简洁明了的是:

def set_email(self, value):
    if '@' not in value:
        raise Exception("This doesn't look like an email address.")
    self._email = value

def get_email(self):
    return self._email

email = property(get_email, set_email)

下面是一篇简短的文章,介绍Python中的getter和setter主题。

我觉得属性是为了让您在真正需要getter和setter时才编写它们。

Java编程文化强烈建议永远不要授予对属性的访问权,相反,只访问实际需要的getter和setter。 总是编写这些显而易见的代码段有点啰嗦,请注意,70%的情况下,它们从未被一些重要的逻辑所取代。

在Python中,人们实际上关心这种开销,因此您可以采用以下实践:

不使用getter和setter在第一次,如果他们不需要 使用@property来实现它们,而不改变其余代码的语法。

喜欢的属性。这就是他们存在的意义。

原因是Python中的所有属性都是公共的。以下划线或两个下划线开头的名称只是一个警告,说明给定的属性是一个实现细节,在将来的代码版本中可能不会保持相同。它不会阻止您实际获取或设置该属性。因此,标准属性访问是访问属性的正常的python方式。

属性的优点是它们在语法上与属性访问相同,因此您可以在不更改客户机代码的情况下从一个属性更改到另一个属性。您甚至可以有一个版本的类使用属性(例如,用于契约代码或调试),而另一个版本的类不用于生产,而不需要更改使用它的代码。与此同时,您不必为所有内容编写getter和setter,以防以后可能需要更好地控制访问。

在Python中,你不会仅仅为了好玩而使用getter或setter或属性。首先只使用属性,然后在需要时,最终迁移到属性,而不必使用类更改代码。

确实有很多带有.py扩展名的代码在任何地方都使用getter和setter、继承和无意义的类,例如一个简单的元组就可以了,但这是人们使用Python用c++或Java编写的代码。

这不是Python代码。