是否有一种方法将装饰器应用于需要有关类的信息的Python方法? [英] Is there a way apply a decorator to a Python method that needs informations about the class?

查看:108
本文介绍了是否有一种方法将装饰器应用于需要有关类的信息的Python方法?的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

当你装饰一个方法时,它没有绑定到类,并且因此没有 im_class 属性。我寻找一种方法来获得关于装饰器里的类的信息。我试过这个:

When you decorate a method, it is not bound yet to the class, and therefor doesn't have the im_class attribute yet. I looking for a way to get the information about the class inside the decorator. I tried this:

import types

def decorator(method):

    def set_signal(self, name, value):
        print name
        if name == 'im_class':
            print "I got the class"

    method.__setattr__ = types.MethodType(set_signal, method)

    return method


class Test(object):
    @decorator
    def bar(self, foo):
        print foo

但它不打印任何东西。

But it doesn't print anything.

我可以想象这样做:

class Test(object):
    @decorator(klass=Test)
    def bar(self, foo):
        print foo

$ b

推荐答案

__ setattr __ 仅在显式 object.attribute = 赋值时调用;构建类不使用属性分配,而是构建一个字典( Test .__ dict __ )。

__setattr__ is only called on explicit object.attribute = assignments; building a class does not use attribute assignment but builds a dictionary (Test.__dict__) instead.

但你有几个不同的选项:

To access the class you have a few different options though:


  1. 使用类装饰器;它将在构建完成后传递完成的类,您可以通过在类中替换它们来装饰该类上的各个方法。您可以使用函数装饰器和类装饰器的组合来标记要装饰的方法:

  1. Use a class decorator instead; it'll be passed the completed class after building it, you could decorate individual methods on that class by replacing them (decorated) in the class. You could use a combination of a function decorator and a class decorator to mark which methods are to be decorated:

def methoddecoratormarker(func):
    func._decorate_me = True
    return func

def realmethoddecorator(func):
    # do something with func. 
    # Note: it is still an unbound function here, not a method!
    return func

def classdecorator(klass):
    for name, item in klass.__dict__.iteritems():
        if getattr(item, '_decorate_me', False):
            klass.__dict__[name] = realmethoddecorator(item)

一个元类,而不是一个类装饰器来实现相同的,当然。

You could use a metaclass instead of a class decorator to achieve the same, of course.

欺骗,并使用 sys._getframe() 从调用框架中检索类: / p>

Cheat, and use sys._getframe() to retrieve the class from the calling frame:

import sys

def methoddecorator(func):
     callingframe = sys._getframe(1)
     classname = callingframe.f_code.co_name

请注意, em> name ;该类本身仍在构建的时候。您可以向 callingframe.f_locals (映射)中添加项目,它们将成为新类对象的一部分。

Note that all you can retrieve is the name of the class; the class itself is still being built at this time. You can add items to callingframe.f_locals (a mapping) and they'll be made part of the new class object.

每当调用方法时访问 self self 是对实例的引用,并且 self .__ class __

Access self whenever the method is called. self is a reference to the instance after all, and self.__class__ is going to be, at the very least, a sub-class of the original class the function was defined in.

这篇关于是否有一种方法将装饰器应用于需要有关类的信息的Python方法?的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆