[Python-ideas] staticmethod and classmethod should be callable

Jeroen Demeyer J.Demeyer at UGent.be
Wed Jun 20 05:56:05 EDT 2018


While working on PEP 579 and friends, I noticed one oddity with 
classmethods: for Python classes, the object stored in the class 
__dict__ is of type "classmethod". For extension types, the type is 
"classmethod_descriptor". In turns out that the latter is callable 
itself, unlike staticmethod or classmethod instances:

 >>> fromhex = float.__dict__["fromhex"]
 >>> type(fromhex)
<class 'classmethod_descriptor'>
 >>> fromhex(float, "0xff")
255.0

 >>> @classmethod
... def f(cls): pass
 >>> f(float)
Traceback (most recent call last):
   File "<stdin>", line 1, in <module>
TypeError: 'classmethod' object is not callable

Since it makes sense to merge the classes "classmethod" and 
"classmethod_descriptor" (PEP 579, issue 8), one of the above behaviors 
should be changed. Given that adding features is less likely to break 
stuff, I would argue that classmethod instances should become callable.

This would also make classmethod more analogous to function: you can see 
both "function" and "classmethod" as unbound methods. The only thing 
that is different is the binding behavior (binding to the instance vs. 
the class).

Finally, function decorators typically turn functions into a different 
kind of callable. I find it counter-intuitive that @classmethod doesn't 
do that.

And for consistency, also staticmethod instances should be callable.

Are there any reasons to *not* make staticmethod and classmethod callable?


Jeroen.


More information about the Python-ideas mailing list