簡體   English   中英

如何使用派生類中的屬性覆蓋基類中的字段?

[英]How do I override a field in a base class with a property in a derived class?

我有一個使用字段的基類:

class Base(object):
    def __init__(self, member):
        self.member = member

一個派生類,希望將其提升為屬性,並添加一些行為:

class Derived(Base):
    @property
    def member(self):
        return super(Derived, self).member

    @member.setter
    def member(self, value):
        print "intercepting setter"
        super(Derived, self).member = value

但是,這不能正確委托給基類:

>>> d = Derived(0)
intercepting setter

Traceback (most recent call last):
  File "<pyshell#8>", line 1, in <module>
    d = Derived(0)
  File "<pyshell#3>", line 3, in __init__
    self.member = 2
  File "<pyshell#6>", line 9, in member
    super(Derived, self).member = value
AttributeError: 'super' object has no attribute 'member'

我該怎么做?

您正在嘗試訪問超級member ,就好像它是一個類屬性一樣。 試試:

class Derived(Base):
    @property
    def member(self):
        print "intercepting getter"
        return self._member

    @member.setter
    def member(self, value):
        print "intercepting setter"
        self._member = value

我認為將成員推廣到財產是正確的做法。 就像在基類中有一個int成員並將其更改為派生類中的方法一樣。 或者像使用普通方法並將其更改為繼承器中的靜態或類方法。 我想這只是打破了這個概念。

您有幾種方法可以解決此問題。

I.如何引入不同(相似)名稱的屬性,然后轉發對繼承原始名稱的所有訪問權限? 這將非常簡單,不會破壞從基類繼承的任何內容。 但它也不允許攔截對原始成員的訪問(在基類或者什么時候完成)。

II。 完全替換繼承的成員。 這只是意味着將值存儲在不同的成員中並從頭開始創建屬性。 之后再讓它訪問原始商店:

class Base(object):

    def __init__(self, member):
        self.member = member

    def baseAccess(self):
        return self.member

class Derived(Base):
    @property
    def member(self):
        print "getter",
        return self.memberStore

    @member.setter
    def member(self, value):
        print "setter",
        self.memberStore = value

b = Base(24)
print "Base(24)"
print "b.member", b.member
print "b.baseAccess()", b.baseAccess()
d = Derived(23)
print "Derived(23)"
print "d.member", d.member
print "d.baseAccess()", d.baseAccess()

b.member = 43
print "b.member = 43"
print "b.member", b.member
print "b.baseAccess()", b.baseAccess()
d.member = 42
print "d.member = 42"
print "d.member", d.member
print "d.baseAccess()", d.baseAccess()

這是輸出:

Base(24)
b.member 24
b.baseAccess() 24
setter getter Derived(23)
d.member getter 23
d.baseAccess() getter 23
b.member = 43
b.member 43
b.baseAccess() 43
setter d.member = 42
d.member getter 42
d.baseAccess() getter 42

所以所有的攔截器都得到了適當的考慮。

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM