Python属性装饰器– Python @property

时间:2020-02-23 14:43:11  来源:igfitidea点击:

今天我们将学习Python属性装饰器。

Python属性装饰器

正如我们所讨论的,我们可以使用装饰器装饰一个函数。
有一些内置的装饰器。

Python @property是内置装饰器之一。
任何装饰器的主要目的是以这种方式更改类的方法或者属性,以使类的用户无需对其代码进行任何更改。

考虑以下程序段:

class Student:
  def __init__(self, name, marks):
      self.name = name
      self.marks = marks
      self.gotmarks = self.name + ' obtained ' + self.marks + ' marks'

st = Student("Jaki", "25")

print(st.name)
print(st.marks)
print(st.gotmarks)

它将输出如下:

Jaki
25
Jaki obtained 25 marks

现在说我们要更改学生类的名称属性,那么会发生什么?在前面的代码之后添加以下3行:

st.name = "Anusha"
print(st.name)
print(st.gotmarks)

然后输出将是:

注意,名称属性已更改,但是由" gotmarks"属性创建的句子与在初始化学生对象期间设置的句子相同。

但是我们希望在学生姓名更新时也可以更改标记。
这是python属性装饰器的使用。

我们可以使用以下代码解决此问题。

使用Python函数解决上述问题

class Student:
  def __init__(self, name, marks):
      self.name = name
      self.marks = marks
      # self.gotmarks = self.name + ' obtained ' + self.marks + ' marks'

  def gotmarks(self):
      return self.name + ' obtained ' + self.marks + ' marks'

st = Student("Jaki", "25")
print(st.name)
print(st.marks)
print(st.gotmarks())

st.name = "Anusha"
print(st.name)
print(st.gotmarks())

它将输出如下:

Jaki
25
Jaki obtained 25 marks
Anusha
Anusha obtained 25 marks

我们从构造函数中删除了gotmarks属性,并添加了一个名为gotmarks的方法。

因此,现在我们的类中没有名为" gotmarks"的属性,而我们有一个名为" gotmarks()"的方法。

对于此更改,任何使用我的类的用户都将遇到麻烦,因为他们必须用函数调用gotmarks()替换所有属性gotmarks。
假设有1000行代码,那么这对编码器来说将是多么麻烦。

使用Python属性装饰器解决以上问题

因此,我们将使用python属性装饰器以pythonic的方式解决此问题。
请注意以下代码:

@property
def gotmarks(self):
 return self.name + ' obtained ' + self.marks + ' marks'

它将提供与以前相同的输出,并且在打印时,请不要忘记删除标记后的"()"。
只需在功能gotmarks()上方编写@property,即可将其用作属性。

而且我们班的用户甚至都不知道属性标记已被删除,为此我们有一个功能。
这就是属性装饰器如何使我们的代码与客户端代码保持松散耦合的方式。

Python属性设置器

现在假设我们要在更改gotmarks的值时设置name和marks属性。
深入观察代码:

class Student:
  def __init__(self, name, marks):
      self.name = name
      self.marks = marks
      # self.gotmarks = self.name + ' obtained ' + self.marks + ' marks'

  @property
  def gotmarks(self):
      return self.name + ' obtained ' + self.marks + ' marks'

  @gotmarks.setter
  def gotmarks(self, sentence):
      name, rand, marks = sentence.split(' ')
      self.name = name
      self.marks = marks

st = Student("Jaki", "25")
print(st.name)
print(st.marks)
print(st.gotmarks)
print("##################")
st.name = "Anusha"
print(st.name)
print(st.gotmarks)
print("##################")
st.gotmarks = 'Golam obtained 36'
print(st.gotmarks)
print(st.name)
print(st.marks)

因为我们要在设置gotmarks的值时更新name和mark的值。
因此,使用@proprety装饰器的'setter'我们可以实现这一点。

注意,我们已经编写了" @ gotmarks.setter",这意味着我们将setter应用于gotmarks方法。
然后我们拆分句子并更新名称和标记的值。

上面的带有setter的python属性装饰器将产生以下输出。

Jaki
25
Jaki obtained 25 marks
##################
Anusha
Anusha obtained 25 marks
##################
Golam obtained 36 marks
Golam
36