Python Forum
@staticmethod and @classmethod
Thread Rating:
  • 0 Vote(s) - 0 Average
  • 1
  • 2
  • 3
  • 4
  • 5
@staticmethod and @classmethod
#1
hi
the below code is in address:
https://python101.pythonlibrary.org/chap...ators.html
# decorator in python: @staticmethod & @classmethod usage
# from address:https://python101.pythonlibrary.org/chapter25_decorators.html


class DecoratorTest(object):
    """
    Test regular method vs @classmethod vs @staticmethod
    """

    def __init__(self):
        """Constructor"""
        pass

    def doubler(self, x):
        """"""
        print("running doubler")
        return x*2

    @classmethod
    def class_tripler(klass, x):
        """"""
        print("running tripler: %s" % klass)
        return x*3

    @staticmethod
    def static_quad(x):
        """"""
        print("running quad")
        return x*4

if __name__ == "__main__":
    decor = DecoratorTest()
    print(f"decor.doubler(5) results: {decor.doubler(5)}" )
    print("-"*50)
    print(f"decor.class_tripler(3) results: {decor.class_tripler(3)}")
    print("-"*50)
    print(f"DecoratorTest.class_tripler(3) results:{DecoratorTest.class_tripler(3)}" )
    print("-"*50)
    print(f"DecoratorTest.static_quad(2) results: {DecoratorTest.static_quad(2)}")
    print("-"*50)
    print(f"decor.static_quad(3) results: {decor.static_quad(3)}")
    print("-"*50)
    print("-"*50)
    print("-"*50)
    print(f"decor.doubler results: {decor.doubler}")
    print("-"*50)
    print(f"decor.class_tripler results: {decor.class_tripler}")
    print("-"*50)
    print(f"decor.static_quad results: {decor.static_quad}")
    print("-"*50)
my questions :
1)what is the klass argument in def class_tripler(klass, x)? if I write decor.class_tripler('test',3), causes a TypeError error message, but the method has two arguments.
2) On the same page is written that
Quote:You will also note that the last print statement shows that decor.static_quad returns a regular function instead of a bound method.
. what are the meanings of regular function and bound function?
thanks
Reply
#2
(Jan-01-2024, 07:30 AM)akbarza Wrote: what is the klass argument in def class_tripler(klass, x)?
The klass argument is an implicit argument which value is the calling class
>>> class A:
...     @classmethod
...     def foo(klass, x):
...         return (klass, x)
... 
>>> A.foo(3)
(<class '__main__.A'>, 3)
>>> class B(A):
...     pass
... 
>>> B.foo(4)
(<class '__main__.B'>, 4)
(Jan-01-2024, 07:30 AM)akbarza Wrote: what are the meanings of regular function and bound function?
A bound method is a small box containing an object and a function. The object is the implicit argument of the function. This bound method is callable with the rest of the arguments. In the following example, c is an instance of class C and c.spam is a bound method containing the object c and the method spam.
>>> class C:
...     def spam(self, x):
...         return (self, x)
... 
>>> c = C()
>>> c
<__main__.C object at 0x7fe88a394d90>
>>> c.spam
<bound method C.spam of <__main__.C object at 0x7fe88a394d90>>
>>> c.spam(3)
(<__main__.C object at 0x7fe88a394d90>, 3)
A bound method is very close to a partial function as returned by functools.partial(). It is an example of curried function.
akbarza likes this post
« We can solve any problem by introducing an extra level of indirection »
Reply
#3
Quote:1)what is the klass argument in def class_tripler(klass, x)? if I write decor.class_tripler('test',3), causes a TypeError error message, but the method has two arguments.
Always post error messages. When I run your code with "def class_tripler(klass, x)" I get this error:
Error:
TypeError: DecoratorTest.class_tripler() takes 2 positional arguments but 3 were given
If I was confused about what was happpening I would modify the class_tripler() method to take three arguments to see what they are.
    @classmethod
    def class_tripler(klass, x, y):
        print(f"klass {klass}, x {x}, y {y}")
        print("running tripler: %s" % klass)
        return x*3
When run I get this output:
Output:
klass <class '__main__.DecoratorTest'>, x test, y 3 running tripler: <class '__main__.DecoratorTest'>
Where does "<class '__main__.DecoratorTest'>" come from? I didn't pass that. Wondering what could make that happen I google "python @classmethod". Among the many useful hits I pick this:

https://docs.python.org/3/library/functi...lassmethod
Quote:@classmethod
Transform a method into a class method.

A class method receives the class as an implicit first argument, just like an instance method receives the instance.
This not only explains why the "extra" argument appears but uses the more conventional "cls" naming of the first argument.

On the same page they discuss @staticmethod
Quote:@staticmethod
Transform a method into a static method.

A static method does not receive an implicit first argument.
Unlike an instance method or a class method, a static method is not implicitly passed an instance or a class object as the first argument. That might be what is mean by not being "bound", because the function/method is not bound to any particular instance or class object. The only thing that differentiates a static method from a function is scope. Functions exist in global or enclosed scope. static methods exist in class scope. You need to use the class name to call a static method.
akbarza likes this post
Reply


Possibly Related Threads…
Thread Author Replies Views Last Post
  Decorator staticmethod Use Cases Devarishi 3 2,763 May-20-2019, 04:27 AM
Last Post: Devarishi
  How I can recognize that member is classmethod of staticmethod? AlekseyPython 0 1,891 Feb-17-2019, 07:01 AM
Last Post: AlekseyPython
  How can i call classmethod with myClass() instead of using myClass.myClassMethod() harun2525 9 5,671 Mar-23-2017, 10:14 PM
Last Post: Larz60+

Forum Jump:

User Panel Messages

Announcements
Announcement #1 8/1/2020
Announcement #2 8/2/2020
Announcement #3 8/6/2020