web-dev-qa-db-ja.com

静的メソッドを宣言するために、pythonに@staticmethodデコレータが本当に必要ですか?

メソッドをstaticとして宣言するために_@staticmethod_デコレータが必要な理由について知りたいです。私はPythonの静的メソッドについて読んでいましたが、静的メソッドはそのクラスをインスタンス化しなくても呼び出し可能であることがわかりました。だから私は以下の2つの例を試しましたが、どちらも同じことをします:

_class StatMethod:
  def stat():
    print("without Decorator")

class StatMethod_with_decorator:
  @staticmethod
  def stat():
    print("With Decorator")
_

クラスでstat()メソッドを直接呼び出すと、どちらも以下の値を出力/表示します。

_>> StatMethod.stat()
without Decorator
>> StatMethod_with_decorator.stat()
With Decorator
_
24
Sanjay

クラスではなく、クラスのインスタンスから@staticmethodを直接呼び出そうとする場合は、デコレータが必要です。

class Foo():
    def bar(x):
        return x + 5

>>> f = Foo()
>>> f.bar(4)
Traceback (most recent call last):
  File "<pyshell#7>", line 1, in <module>
    f.bar(4)
TypeError: bar() takes 1 positional argument but 2 were given

@staticmethodを宣言すると、self引数は最初の引数として暗黙的に渡されません

class Foo():
    @staticmethod
    def bar(x):
        return x + 5

>>> f = Foo()
>>> f.bar(4)
9
34
CoryKramer

documentation は、ユーザー定義のメソッドを呼び出すときに行われるいくつかの変換について説明しています。

関数オブジェクトから(非バインドまたはバインド済み)メソッドオブジェクトへの変換は、属性がクラスまたはインスタンスから取得されるたびに発生することに注意してください。場合によっては、ローカル変数に属性を割り当て、そのローカル変数を呼び出すことで、実りの多い最適化が得られます。また、この変換はユーザー定義関数でのみ発生することにも注意してください。他の呼び出し可能オブジェクト(およびすべての呼び出し不可オブジェクト)は、変換なしで取得されます。また、クラスインスタンスの属性であるユーザー定義関数は、バインドされたメソッドに変換されないことに注意することも重要です。これは、関数がクラスの属性である場合にのみ発生します。

Staticmethodとしてマークされたメソッドの場合、これは異なります。

静的メソッドオブジェクトは、関数オブジェクトから上記のメソッドオブジェクトへの変換を無効にする方法を提供します。静的メソッドオブジェクトは、他のオブジェクト(通常はユーザー定義のメソッドオブジェクト)のラッパーです。静的メソッドオブジェクトがクラスまたはクラスインスタンスから取得される場合、実際に返されるオブジェクトはラップされたオブジェクトであり、これ以上の変換は行われません。静的メソッドオブジェクト自体は呼び出し可能ではありませんが、通常、ラップするオブジェクトは呼び出し可能です。静的メソッドオブジェクトは、組み込みのstaticmethod()コンストラクターによって作成されます。

2
Flurin

関数にいくつかのパラメーターがある場合、非静的メソッドの呼び出しは失敗します

静的メソッドはクラスのローカル変数を使用しませんでしたが、クラスメソッドは

1
Jimmy Guo