Python 确定方法的类

Python 确定方法的类,python,Python,假设我有: class User(): def method(self): pass u=User() 如何通过accessdecorator从u.method提取类?我从u方法中得到的只是它是一个函数。。。但是我想知道从哪个类 我对Python2.7解决方案感兴趣 更新:我忘了提到我没有提供足够的细节: class access(): """ Decorator for specifying which 'access right' must be enforc

假设我有:

class User():
  def method(self):
    pass

u=User()
如何通过
access
decorator从
u.method
提取类?我从u方法中得到的只是它是一个函数。。。但是我想知道从哪个

我对Python2.7解决方案感兴趣

更新:我忘了提到我没有提供足够的细节:

class access():
    """
    Decorator for specifying which 'access right' must be enforced 
    at the object method level  
    """

    def __init__(self, right):
        self.right=right

    def __call__(self, method):
      ### need to grab the method's class name here
我实际上在使用一个装饰器:

class User():
  @access("edit"
  def method(self):
    pass

使用
u.method.im\u类

In [3]: u.method.im_class
Out[3]: __main__.User

用户定义的方法 ... 特殊只读属性:
im\u self
为类实例对象,
im\u func
为函数对象
im_类
是绑定方法的im_self类或请求未绑定方法的im_self类

在Python3中,通过
\uuuuu self\uuu
查找类:

>>> u.method.__self__.__class__
<class '__main__.User'>
>>u.method.\uuuuuu self.\uuuu类__

使用
u.method.im\u类

In [3]: u.method.im_class
Out[3]: __main__.User

用户定义的方法 ... 特殊只读属性:
im\u self
为类实例对象,
im\u func
为函数对象
im_类
是绑定方法的im_self类或请求未绑定方法的im_self类

在Python3中,通过
\uuuuu self\uuu
查找类:

>>> u.method.__self__.__class__
<class '__main__.User'>
>>u.method.\uuuuuu self.\uuuu类__
为什么不直接打印呢

class User():
  def method(self):
    pass

u=User()

print(u.method)
输出:

<bound method User.method of <__main__.User object at 0x02D59510>>
<class '__main__.User'>
输出:

<bound method User.method of <__main__.User object at 0x02D59510>>
<class '__main__.User'>

这两种方法都证实在python
2.7.3
和python
3.3

中有效,为什么不直接打印它呢

class User():
  def method(self):
    pass

u=User()

print(u.method)
输出:

<bound method User.method of <__main__.User object at 0x02D59510>>
<class '__main__.User'>
输出:

<bound method User.method of <__main__.User object at 0x02D59510>>
<class '__main__.User'>


这两种方法都证实在python
2.7.3
和python
3.3
中工作。您的装饰程序不是用方法调用的,而是用函数调用的

类还不存在,将函数绑定到类的未绑定方法也不存在,更不用说类的任何实例以及将函数绑定到该实例的绑定方法了。而且,即使这些方法确实存在,它们也将围绕您的装饰程序返回的函数构建

因此,您不能内省收到的函数来尝试获取其类,因为它没有类


<> P>有很多不同的技巧可以用来确定你在定义中的内容(尽管它们可能针对特定的Python实现和版本),但是没有干净的方法来做你想做的事情。例如,这里有一个可怕的黑客:

self.classname = sys._getframe(1).f_code.co_name
这是什么意思?好吧,你的装饰器本身就是第0帧;不管叫什么,都是第一帧。如果调用它的对象是类定义,那么它的
code
对象将使用该类的名称作为其类。你仍然不能真正访问这个类,因为它不存在(直到代码被执行,它正在发生的中间)。但是,如果您知道该名称永远不会被覆盖,您可以只存储该名称,然后在调用时查找它(您可能还希望
f_locals['''u____']
查找它),以获取该类


然而,一个更好的解决方案是创建一个类装饰器和一个使用它的方法装饰器。诀窍在于,方法装饰器以某种方式“注册”它们希望(它们返回的函数)被“修复”。然后,类装饰器遍历注册的方法并修复它们

例如:

def class_deco(cls):
    for name, method in inspect.getmembers(cls, callable):
        if hasattr(method, 'class_fixup'):
            method.class_fixup(cls)
    return cls

现在,您的方法装饰器仍然无法在调用时访问该类,但它可以创建一个“fixup”函数,在类准备好时完成装饰,然后只需在
返回f
之前执行
fixup=fixup
,您的装饰器不是用方法调用的,而是用函数调用的

类还不存在,将函数绑定到类的未绑定方法也不存在,更不用说类的任何实例以及将函数绑定到该实例的绑定方法了。而且,即使这些方法确实存在,它们也将围绕您的装饰程序返回的函数构建

因此,您不能内省收到的函数来尝试获取其类,因为它没有类


<> P>有很多不同的技巧可以用来确定你在定义中的内容(尽管它们可能针对特定的Python实现和版本),但是没有干净的方法来做你想做的事情。例如,这里有一个可怕的黑客:

self.classname = sys._getframe(1).f_code.co_name
这是什么意思?好吧,你的装饰器本身就是第0帧;不管叫什么,都是第一帧。如果调用它的对象是类定义,那么它的
code
对象将使用该类的名称作为其类。你仍然不能真正访问这个类,因为它不存在(直到代码被执行,它正在发生的中间)。但是,如果您知道该名称永远不会被覆盖,您可以只存储该名称,然后在调用时查找它(您可能还希望
f_locals['''u____']
查找它),以获取该类


然而,一个更好的解决方案是创建一个类装饰器和一个使用它的方法装饰器。诀窍在于,方法装饰器以某种方式“注册”它们希望(它们返回的函数)被“修复”。然后,类装饰器遍历注册的方法并修复它们

例如:

def class_deco(cls):
    for name, method in inspect.getmembers(cls, callable):
        if hasattr(method, 'class_fixup'):
            method.class_fixup(cls)
    return cls

现在,您的方法装饰器仍然无法在调用时访问该类,但它可以创建一个“fixup”函数,在类准备就绪时完成装饰,然后只需在
返回f

AttributeError之前执行
f.class\u fixup=fixup
,'function'对象没有属性'im\u class'@PavelAnossov:no,这只会给你
内置的方法!Python3没有与
im_类
等价的类(因为它只适用于不存在的未绑定方法)。你想要
\uuuuuuuuuuuuuuuuuuuuuuuuuuuuuuuuuuuuuuuuuuuuuuuuuuuuuuuuuuuuuuuuuuuuuuuuuuuuuuuuuuuuuuuuuuuuuuuuuuuuuuuuuuuuuuu