0

Consider:

class cla(object):
    def __init__(self,val):
        self.val = val

    def met(self):
        return self.val + 1

Then cla.met(cla(1)) returns 2.

Since I don't need an instance of class cla to use method met, does this mean it is a class method, even though I haven't used the decorator @classmethod?

I read https://julien.danjou.info/blog/2013/guide-python-static-class-abstract-methods to understand better what class methods are, but somehow it seems to me that the intended meaning of @classmethod is already present in the normal methods of a class - and I'm actually quite confused from the examples for there, as they don't even compile.

l7ll7
  • 1,309
  • 1
  • 10
  • 20

2 Answers2

1

If you have an instance of class cla:

instance = cla(1)

Then the following two calls are equivalent:

instance.met()
cla.met(instance)

Note that the second only works if you pass it an argument with a val attribute (so you actually do need sth. resembling an instance of class cla), while the first implicitly calls the function defined on the class and passes itself as an argument. See docs on method objects. The following lines could help shed some light on the internals of a method object:

>>> f = cla.met
>>> m = instance.met
>>> type(f)
<class 'function'>
>>> type(m)
<class 'method'>
>>> m.__self__ == instance
True
>>> m.__func__ == f
True

So

>>> f(instance)
2

is the same as

>>> m.__func__(m.__self__)
2

which is what instance.met() (aka m() aka m.__call__()) does under the hood.

Ilja Everilä
  • 50,538
  • 7
  • 126
  • 127
user2390182
  • 72,016
  • 6
  • 67
  • 89
1

cla.met(cla(1)) is just a convoluted way of saying cla(1).met(). The answer is simply no: met is not a class method.

A class method would be

class cla():
   @classmethod
   def met(cls, val):
       return val + 1

which would be called as cla.met(1)

Hope this clarifies the difference.

Stefano M
  • 4,267
  • 2
  • 27
  • 45