、あなただけ@some_decorator(first_method)
を言うことができ、それが動作しますが、すべてのメソッドは、クラスでの通常の機能であるためコンテナとして。
Python 2では、バインドされたバインドされていない、インスタンス、クラス、および静的メソッドの複雑なシステムがあります。このため、クラス定義の内側(完全に形成されている場合はクラスまで)にfirst_method
にアクセスすることはできません。
少し問題を回避するには、二つのクラスにそのクラスを分割するために、次のようになります。
class BaseA(object):
def first_method(self):
print "I'm the first method!"
class A(BaseA):
@some_decorator(BaseA.first_method)
def second_method(self):
print "I'm the second method!"
ないすべてのケースのための最善の解決策が、動作します。また
、覚えておいて、それはここで宣言されたように両方のケース(PY2 & PY3を)に、デコレータはfirst_method
を参照すること。任意の子孫クラスがメソッドを再定義すると、新しいメソッドはデコレータで使用されません。親のものだけが使用されます。
恐らく、first_method
を参照しないでください。代わりに、ちょうどself
/cls
デコレータのラッパーの最初の位置引数を受け入れ、そこself.first_method
/cls.first_method
を使用します。
import functools
def some_decorator(fn):
@functools.wraps(fn)
def wrapper(self, *args, **kwargs):
first_method = self.first_method
first_method()
return fn(self, *args, **kwargs)
return wrapper
class A(object):
def first_method(self):
print "I'm the first method of A!"
@some_decorator
def second_method(self):
print "I'm the second method!"
class B(A):
def first_method(self):
print "I'm the first method of B!"
A().second_method()
# I'm the first method of A!
# I'm the second method!
B().second_method()
# I'm the first method of B!
# I'm the second method!
あなたはその方法は、設定したい場合:
def some_decorator(method_name):
def decorator(fn):
@functools.wraps(fn)
def wrapper(self, *args, **kwargs):
first_method = getattr(self, method_name)
first_method()
return fn(self, *args, **kwargs)
return wrapper
return decorator
class A(object):
def first_method(self):
print "I'm the first method of A!"
@some_decorator('first_method')
def second_method(self):
print "I'm the second method!"
class B(A):
def first_method(self):
print "I'm the first method of B!"
私はこの小さなブログの記事を考えます有用であるかもしれません:http://scottlobdell.me/2015/04/decorators-arguments-python/ – freddiev4
@ FreddieV4、私は引数を使ってデコレータを作成する方法を知っています。この問題は、前述したように、「A」はそれ自体では定義されていないことである。 'A'の中から関数の外に' first_method'を参照すると、 'A.first_method'ではなく' unbound'メソッド 'first_method'が返されます。 –