Combination of functools.partialmethod and classmethod
<p>I would like to use <code>functools.partialmethod</code> on a classmethod. However the behavior I find is not what I would expect (and like to have).
Here is an example:</p>

<pre><code>class A(object):
    @classmethod
    def h(cls, x, y):
        print(cls, x, y)

class B(A):
    h = functools.partialmethod(A.h, "fixed")
</code></pre>

<p>When I do</p>

<pre><code>&gt;&gt;&gt; b = B()
&gt;&gt;&gt; b.h(3)
</code></pre>

<p>I get an error:</p>

<pre><code>...
TypeError: h() takes 3 positional arguments but 4 were given
</code></pre>

<p>This is consistent with</p>

<pre><code>&gt;&gt;&gt; b.h()
&lt;class '__main__.A'&gt; &lt;__main__.B object at 0x1034739e8&gt; fixed
</code></pre>

<p>However, I would expect (and like to have) the following behavior:</p>

<pre><code>&gt;&gt;&gt; b.h(4)
&lt;class '__main__.B'&gt; fixed 4
</code></pre>

<p>I think that <code>functools.partialmethod</code> treats <code>B.h</code> as a normal instance method and passes the actual instance as first argument automatically.
But this behavior renders <code>functools.partialmethod</code> useless for freezing arguments in classmethods of inheriting classes.</p>

<p>Use <a href="https://docs.python.org/3/library/functions.html#super" rel="nofollow"><code>super</code></a> (v2.7)</p>

<pre><code>class A(object):
    @classmethod
    def c(cls, x, y):
        print('cls:{}, x:{}, y:{}'.format(cls, x, y))

class B(A):
    def c(self, y):
        super(B, self).c(x = 'fixed', y = y) 

class C(A):
    def c(self, x):
        super(C, self).c(x = x, y = 'fixed') 

b = B()
c = C()

&gt;&gt;&gt; 
&gt;&gt;&gt; b.c(4)
cls:&lt;class '__main__.B'&gt;, x:fixed, y:4
&gt;&gt;&gt; c.c(4)
cls:&lt;class '__main__.C'&gt;, x:4, y:fixed
&gt;&gt;&gt; 
</code></pre>

<hr>

<p><a href="https://rhettinger.wordpress.com/2011/05/26/super-considered-super/" rel="nofollow">super is super</a></p>

python python-3.x python-3.5 class-method functools