10

次のように定義されたオブジェクトがあります

class a():
    @property
    def prop(self):
        print("hello from object.prop")
        @property
        def prop1(self):
            print("Hello from object.prop.prop")

電話すると

>>> obj = a()
>>> obj.prop
hello from object.prop
>>> obj.prop.prop

次のトレースバック エラーが発生します

Traceback (most recent call last):
  File "object_property.py", line 13, in <module>
    a.prop.prop1
AttributeError: 'NoneType' object has no attribute 'prop1'

私が把握しようとしているのは、オブジェクトのネストされたプロパティを定義できるかどうかです。

4

2 に答える 2

11

トレースバックは、プロパティにreturnステートメントがないためです。したがって、 を返しますNoneType。これは明らかに独自の属性を持つことはできません。あなたのプロパティはおそらく、独自のprop属性を持つ別のクラスのインスタンスを返す必要があります。このようなもの:

class a():
    def __init__(self):
        self.b = b()
    @property
    def prop(self):
        print("hello from object.prop")
        return self.b

class b():
    @property
    def prop(self):
        print("Hello from object.prop.prop")

x = a()
print x.prop.prop
>> hello from object.prop
>> Hello from object.prop.prop
>> None
于 2013-07-29T01:34:29.087 に答える
4

一般に、いいえ、自分以外のオブジェクトの属性アクセスをラップする方法はありません。確かに、きれいにネストできる構文はありません (プロパティ関数内でクラスを宣言できますが、すぐに見苦しくなります)。

つまり、 のような式obj.prop_a.prop_bでは、最上位のオブジェクトは、別のオブジェクトで発生している属性アクセスでobj何が起こるかを直接制御することはできません。prop_b

例として、次の一連のステートメントを考えてみましょう。

foo = obj.prop_a
bar = foo.prop_b

に割り当てられた値barは と同じですobj.prop_a.prop_bが、そのステートメントは直接参照していませんでしたobj

ラッパー オブジェクトのあいまいな世界に足を踏み入れたいのであれば、やりたいことができるかもしれませんが、基本的なプロパティほどきちんとしたものにはなりません。@ qwwqwwqの回答のようにobj.prop_a、独自の@property装飾された functionを持つクラスのインスタンスを返すことができますprop_b

prop_a外部からアクセスできることを心配していなければ、関数内でクラスを宣言することもできます。ただし、複雑なものについては、すぐに面倒になります。

代わりに、 を介してアクセスできるようにしたいものを、 などの でobj.prop_a.prop_b直接プロパティまたはメソッドを介してより適切に公開できるかどうかを検討してください。この方法で、はるかに優れたデザインを見つけることができると思います。objobj.prop_a_b

于 2013-07-29T03:21:18.237 に答える