tags:

views:

40

answers:

1
#!/usr/bin/python

class Bar(object):

  @staticmethod
  def ruleOn(rule):
    if isinstance(rule, tuple):
      print rule[0]
      print rule[0].__get__(None, Foo)
    else:
      print rule

class Foo(object):

  @classmethod
  def callRule(cls):
    Bar.ruleOn(cls.RULE1)
    Bar.ruleOn(cls.RULE2)


  @classmethod
  def check(cls):
    print "I am check"

  RULE1   = check
  RULE2   = (check,)

Foo.callRule()


---- output ----
<bound method type.check of <class '__main__.Foo'>>
<classmethod object at 0xb7d313a4>
<bound method type.check of <class '__main__.Foo'>>

As you can see the trying to store a reference to a classmethod function in a tuple for future use.
However it seems to store the object itself rather then reference to the bound function
As you see it works for a variable reference.
The only way to get it is to use __get__ which requires the name of the class it belongs to
which is not available at the time of the RULE variable assignment.

Any ideas anyone?
A: 

This is because method are actually functions in Python. They only become bound methods when you look them up on the constructed class instance. See my answer to this question for more details. The non-tuple variant works because it is conceptually the same as accessing a classmethod.

If you want to assign bound classmethods to class attributes you'll have to do that after you construct the class:

class Foo(object):
    @classmethod
    def callRule(cls):
        Bar.ruleOn(cls.RULE1)
        Bar.ruleOn(cls.RULE2)

    @classmethod
    def check(cls):
        print "I am check"

 Foo.RULE1 = Foo.check
 Foo.RULE2 = (Foo.check,)
Ants Aasma
Thank you, this makes sense.Just out of curiosityIs there any way to retrieve class name during its construction?
No. The class object doesn't exist while the class body is executing. The best you could do is to bind the functions using a class decorator or a metaclass.
Ants Aasma
thank you again