运行下面的代码会引发以下异常:

ERROR!
Traceback (most recent call last):
  File "<string>", line 22, in <module>
TypeError: MyDecorator.__init__() takes 2 positional arguments but 4 were given
> 

当从类子类派生的对象被实例化时,我希望访问从我的修饰器代码中提供给构造函数的所有参数.我之前不得不停止,因为我当前的代码 destruct 了继承.有谁能为我指引正确的方向吗?

class MyDecorator:
    def __init__(self, original_class):
        self.original_class = original_class

    def __call__(self, *args, **kwargs):
        instance = self.original_class(*args, **kwargs)
        print(f"Decorator: Creating instance with arguments: {args}, {kwargs}")
        return instance

    def __getattr__(self, name):
        # Pass through attribute access to the original class
        return getattr(self.original_class, name)

@MyDecorator
class BaseClass:
    def __init__(self, arg1, arg2):
        self.arg1 = arg1
        self.arg2 = arg2

class SubClass(BaseClass):
    def additional_method(self):
        print("Additional method in SubClass")

# Creating an instance of the decorated base class
base_instance = BaseClass("foo", arg2="bar")
print(f"arg1: {base_instance.arg1}, arg2: {base_instance.arg2}")

# Creating an instance of the decorated subclass
sub_instance = SubClass("baz", arg2="qux")
print(f"arg1: {sub_instance.arg1}, arg2: {sub_instance.arg2}")

# Accessing additional method in the subclass
sub_instance.additional_method()

推荐答案

在 comments 中讨论之后,我意识到自定义元类将是一个简单的解决方案.当您实例化一个类时,您实际上是在调用类‘CLASS’__call__方法,它是元类‘__call__.

您可以在那里进行拦截:

class MyMeta(type):
    def __call__(self, *args, **kwargs):
        print(f"Creating instance with arguments: {args}, {kwargs}")
        return super().__call__(*args, **kwargs)


class BaseClass(metaclass=MyMeta):
    def __init__(self, arg1, arg2):
        self.arg1 = arg1
        self.arg2 = arg2


class SubClass(BaseClass):
    def additional_method(self):
        print("Additional method in SubClass")


# Creating an instance of the decorated base class
base_instance = BaseClass("foo", arg2="bar")
print(f"arg1: {base_instance.arg1}, arg2: {base_instance.arg2}")

# Creating an instance of the decorated subclass
sub_instance = SubClass("baz", arg2="qux")
print(f"arg1: {sub_instance.arg1}, arg2: {sub_instance.arg2}")

# Accessing additional method in the subclass
sub_instance.additional_method()

输出:

Creating instance with arguments: ('foo',), {'arg2': 'bar'}
arg1: foo, arg2: bar
Creating instance with arguments: ('baz',), {'arg2': 'qux'}
arg1: baz, arg2: qux
Additional method in SubClass

关键是元类适用于整个继承链.

现在好多了,因为isinstance()正常工作.在您的解决方案中,BaseClass的类型将变为MyDecorator,这是错误的.

Python相关问答推荐

如何对行使用分段/部分.diff()或.pct_change()?

Pandas read_jsonfuture 警告:解析字符串时,to_datetime与单位的行为已被反对

使用Python Great Expectations和python-oracledb

合并同名列,但一列为空,另一列包含值

如何获取Django REST框架中序列化器内部的外卡属性?

将行从一个DF添加到另一个DF

具有症状的分段函数:如何仅针对某些输入值定义函数?

在Python和matlab中显示不同 colored颜色 的图像

配置Sweetviz以分析对象类型列,而无需转换

如何让 turtle 通过点击和拖动来绘制?

Matlab中是否有Python的f-字符串等效物

根据另一列中的nan重置值后重新加权Pandas列

Pandas 都是(),但有一个门槛

使用@ guardlasses. guardlass和注释的Python继承

如何创建一个缓冲区周围的一行与manim?

在Python中动态计算范围

为一个组的每个子组绘制,

Django RawSQL注释字段

合并与拼接并举

pysnmp—lextudio使用next()和getCmd()生成器导致TypeError:tuple对象不是迭代器''