У меня проблема с определением геттера с использованием @property
в конкретном классе. Вот код питона:Определение @property
from abc import ABCMeta, abstractproperty
class abstract(object):
__metaclass__ = ABCMeta
def __init__(self, value1):
self.v1 = value1
@abstractproperty
def v1(self):
pass
class concrete(abstract):
def __init__(self, value1):
super(concrete, self).__init__(value1)
@property
def v1(self):
return self.v1
Затем проверить код и получаю эту ошибку:
test_concrete = concrete("test1")
test_concrete.v1
---------------------------------------------------------------------------
AttributeError Traceback (most recent call last)
<ipython-input-190-eb896d7ec1c9> in <module>()
----> 1 test_concrete = concrete("test1")
2 test_concrete.v1
<ipython-input-189-bf15021022d3> in __init__(self, value1)
11 class concrete(abstract):
12 def __init__(self, value1):
---> 13 super(concrete, self).__init__(value1)
14
15 @property
<ipython-input-189-bf15021022d3> in __init__(self, value1)
3
4 def __init__(self, value1):
----> 5 self.v1 = value1
6
7 @abstractproperty
AttributeError: can't set attribute
В основном я намерен установить v1
как атрибут только для чтения.
Я привык использовать одно и то же имя для атрибута и его функции getter, но кажется, что я не могу этого сделать, если класс унаследован от абстрактного класса.
Я нашел обходной путь, используя другое имя для функции геттера v1
в get_v1
:
class abstract(object):
__metaclass__ = ABCMeta
def __init__(self, value1):
self.v1 = value1
@abstractproperty
def get_v1(self):
pass
class concrete(abstract):
def __init__(self, value1):
super(concrete, self).__init__(value1)
@property
def get_v1(self):
return self.v1
есть лучший способ решения этой проблемы?
Общепринятая практика - это имена частных атрибутов, таких как '_v1'. – bereal
На самом деле вы не предоставили сеттер для этого объекта, поэтому он доступен только для чтения. Кроме того, вы не можете присвоить атрибуту поддержки то же имя, что и свойство, что не имеет смысла. – jonrsharpe