Static methods in Python?

后端 未结 10 758
悲&欢浪女
悲&欢浪女 2020-11-22 02:36

Is it possible to have static methods in Python which I could call without initializing a class, like:

ClassName.static_method()
相关标签:
10条回答
  • 2020-11-22 02:41

    Yes, check out the staticmethod decorator:

    >>> class C:
    ...     @staticmethod
    ...     def hello():
    ...             print "Hello World"
    ...
    >>> C.hello()
    Hello World
    
    0 讨论(0)
  • 2020-11-22 02:44

    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.

    0 讨论(0)
  • 2020-11-22 02:46

    So, static methods are the methods which can be called without creating the object of a class. For Example :-

        @staticmethod
        def add(a, b):
            return a + b
    
    b = A.add(12,12)
    print b
    

    In the above example method add is called by the class name A not the object name.

    0 讨论(0)
  • 2020-11-22 02:48

    Aside from the particularities of how static method objects behave, there is a certain kind of beauty you can strike with them when it comes to organizing your module-level code.

    # garden.py
    def trim(a):
        pass
    
    def strip(a):
        pass
    
    def bunch(a, b):
        pass
    
    def _foo(foo):
        pass
    
    class powertools(object):
        """
        Provides much regarded gardening power tools.
        """
        @staticmethod
        def answer_to_the_ultimate_question_of_life_the_universe_and_everything():
            return 42
    
        @staticmethod
        def random():
            return 13
    
        @staticmethod
        def promise():
            return True
    
    def _bar(baz, quux):
        pass
    
    class _Dice(object):
        pass
    
    class _6d(_Dice):
        pass
    
    class _12d(_Dice):
        pass
    
    class _Smarter:
        pass
    
    class _MagicalPonies:
        pass
    
    class _Samurai:
        pass
    
    class Foo(_6d, _Samurai):
        pass
    
    class Bar(_12d, _Smarter, _MagicalPonies):
        pass
    

    ...

    # tests.py
    import unittest
    import garden
    
    class GardenTests(unittest.TestCase):
        pass
    
    class PowertoolsTests(unittest.TestCase):
        pass
    
    class FooTests(unittest.TestCase):
        pass
    
    class BarTests(unittest.TestCase):
        pass
    

    ...

    # interactive.py
    from garden import trim, bunch, Foo
    
    f = trim(Foo())
    bunch(f, Foo())
    

    ...

    # my_garden.py
    import garden
    from garden import powertools
    
    class _Cowboy(garden._Samurai):
        def hit():
            return powertools.promise() and powertools.random() or 0
    
    class Foo(_Cowboy, garden.Foo):
        pass
    

    It now becomes a bit more intuitive and self-documenting in which context certain components are meant to be used and it pans out ideally for naming distinct test cases as well as having a straightforward approach to how test modules map to actual modules under tests for purists.

    I frequently find it viable to apply this approach to organizing a project's utility code. Quite often, people immediately rush and create a utils package and end up with 9 modules of which one has 120 LOC and the rest are two dozen LOC at best. I prefer to start with this and convert it to a package and create modules only for the beasts that truly deserve them:

    # utils.py
    class socket(object):
        @staticmethod
        def check_if_port_available(port):
            pass
    
        @staticmethod
        def get_free_port(port)
            pass
    
    class image(object):
        @staticmethod
        def to_rgb(image):
            pass
    
        @staticmethod
        def to_cmyk(image):
            pass
    
    0 讨论(0)
  • 2020-11-22 02:49

    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'])
    
    0 讨论(0)
  • 2020-11-22 02:53

    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

    0 讨论(0)
提交回复
热议问题