Static methods in Python?

2018-12-31 07:36发布

Is it possible to have static methods in Python so I can call them without initializing a class, like:

ClassName.StaticMethod ( )

10条回答
还给你的自由
2楼-- · 2018-12-31 07:57

Perhaps the simplest option is just to put those functions outside of the class:

class Dog(object):
    def __init__(self, name):
        self.name = name

    def bark(self):
        if self.name == "Doggy":
            return barking_sound()
        else:
            return "yip yip"

def barking_sound():
    return "woof woof"

Using this method, functions which modify or use internal object state (have side effects) can be kept in the class, and the reusable utility functions can be moved outside.

Let's say this file is called dogs.py. To use these, you'd call dogs.barking_sound() instead of dogs.Dog.barking_sound.

If you really need a static method to be part of the class, you can use the staticmethod decorator.

查看更多
ら面具成の殇う
3楼-- · 2018-12-31 07:57

I encounter this question from time to time. The use case and example that I am fond of is:

jeffs@jeffs-desktop:/home/jeffs  $ python36
Python 3.6.1 (default, Sep  7 2017, 16:36:03) 
[GCC 6.3.0 20170406] on linux
Type "help", "copyright", "credits" or "license" for more information.
>>> import cmath
>>> print(cmath.sqrt(-4))
2j
>>>
>>> dir(cmath)
['__doc__', '__file__', '__loader__', '__name__', '__package__', '__spec__', 'acos', 'acosh', 'asin', 'asinh', 'atan', 'atanh', 'cos', 'cosh', 'e', 'exp', 'inf', 'infj', 'isclose', 'isfinite', 'isinf', 'isnan', 'log', 'log10', 'nan', 'nanj', 'phase', 'pi', 'polar', 'rect', 'sin', 'sinh', 'sqrt', 'tan', 'tanh', 'tau']
>>> 

It does not make sense to create an object of class cmath, because there is no state in a cmath object. However, cmath is a collection of methods that are all related in some way. In my example above, all of the functions in cmath act on complex numbers in some way.

查看更多
何处买醉
4楼-- · 2018-12-31 08:00

Static methods in Python?

Is it possible to have static methods in Python so I can call them without initializing a class, like:

ClassName.StaticMethod()

Yes, static methods can be created like this (although it's a bit more Pythonic to use underscores instead of CamelCase for methods):

class ClassName(object):

    @staticmethod
    def static_method(kwarg1=None):
        '''return a value that is a function of kwarg1'''

The above uses the decorator syntax. This syntax is equivalent to

class ClassName(object):

    def static_method(kwarg1=None):
        '''return a value that is a function of kwarg1'''

    static_method = staticmethod(static_method)

This can be used just as you described:

ClassName.static_method()

A builtin example of a static method is str.maketrans() in Python 3, which was a function in the string module in Python 2.


Another option that can be used as you describe is the classmethod, the difference is that the classmethod gets the class as an implicit first argument, and if subclassed, then it gets the subclass as the implicit first argument.

class ClassName(object):

    @classmethod
    def class_method(cls, kwarg1=None):
        '''return a value that is a function of the class and kwarg1'''

Note that cls is not a required name for the first argument, but most experienced Python coders will consider it badly done if you use anything else.

These are typically used as alternative constructors.

new_instance = ClassName.class_method()

A builtin example is dict.fromkeys():

new_dict = dict.fromkeys(['key1', 'key2'])
查看更多
只靠听说
5楼-- · 2018-12-31 08:06

Yes, check out the staticmethod decorator:

>>> class C:
...     @staticmethod
...     def hello():
...             print "Hello World"
...
>>> C.hello()
Hello World
查看更多
牵手、夕阳
6楼-- · 2018-12-31 08:10

Yep, using the staticmethod decorator

class MyClass(object):
    @staticmethod
    def the_static_method(x):
        print x

MyClass.the_static_method(2) # outputs 2

Note that some code might use the old method of defining a static method, using staticmethod as a function rather than a decorator. This should only be used if you have to support ancient versions of Python (2.2 and 2.3)

class MyClass(object):
    def the_static_method(x):
        print x
    the_static_method = staticmethod(the_static_method)

MyClass.the_static_method(2) # outputs 2

This is entirely identical to the first example (using @staticmethod), just not using the nice decorator syntax

Finally, use staticmethod() sparingly! There are very few situations where static-methods are necessary in Python, and I've seen them used many times where a separate "top-level" function would have been clearer.


The following is verbatim from the documentation::

A static method does not receive an implicit first argument. To declare a static method, use this idiom:

class C:
    @staticmethod
    def f(arg1, arg2, ...): ...

The @staticmethod form is a function decorator – see the description of function definitions in Function definitions for details.

It can be called either on the class (such as C.f()) or on an instance (such as C().f()). The instance is ignored except for its class.

Static methods in Python are similar to those found in Java or C++. For a more advanced concept, see classmethod().

For more information on static methods, consult the documentation on the standard type hierarchy in The standard type hierarchy.

New in version 2.2.

Changed in version 2.4: Function decorator syntax added.

查看更多
其实,你不懂
7楼-- · 2018-12-31 08:11

Python Static methods can be created in two ways.

  1. Using staticmethod()

    class Arithmetic:
        def add(x, y):
            return x + y
    # create add static method
    Arithmetic.add = staticmethod(Arithmetic.add)
    
    print('Result:', Arithmetic.add(15, 10))
    

Output:

Result: 25

  1. Using @staticmethod

    class Arithmetic:
    
    # create add static method
    @staticmethod
    def add(x, y):
        return x + y
    
    print('Result:', Arithmetic.add(15, 10))
    

Output:

Result: 25

查看更多
登录 后发表回答