Python 存储类及其子类的init参数
我有一个类,我希望能够存储在创建该类或任何子类(子类init的参数比超类多)的新实例时给出的参数的名称和值 目前我用这个函数装饰我所有子类的init,这就是我的工作。 但是,有没有一种方法可以在不装饰每个init的情况下获得相同的效果? 环顾四周,我看到元类做了一些类似的事情,但我从来没有使用过它们,我也找不到一种方法在这里应用它们Python 存储类及其子类的init参数,python,python-3.x,class,python-decorators,Python,Python 3.x,Class,Python Decorators,我有一个类,我希望能够存储在创建该类或任何子类(子类init的参数比超类多)的新实例时给出的参数的名称和值 目前我用这个函数装饰我所有子类的init,这就是我的工作。 但是,有没有一种方法可以在不装饰每个init的情况下获得相同的效果? 环顾四周,我看到元类做了一些类似的事情,但我从来没有使用过它们,我也找不到一种方法在这里应用它们 提前谢谢 您不需要更改为仅使用关键字args,也可以捕获位置。或多或少,您将适应任何存储和访问args的方式: class C: def __init__(
提前谢谢 您不需要更改为仅使用关键字args,也可以捕获位置。或多或少,您将适应任何存储和访问args的方式:
class C:
def __init__(self, *args, **kwargs):
self.called_with = dict(
name = self.__class__,
positionals = args,
keywords = kwargs
)
print(args, kwargs)
class D(C):
pass
c1 = C(1,2,3,a='A',b='B')
print(c1.called_with['name'])
print(c1.called_with['positionals'])
print(c1.called_with['keywords'])
print()
d1 = D(1,2,3,4,d='D')
print(d1.called_with['name'])
print(d1.called_with['positionals'])
print(d1.called_with['keywords'])
输出:
(1, 2, 3) {'a': 'A', 'b': 'B'}
<class '__main__.C'>
(1, 2, 3)
{'a': 'A', 'b': 'B'}
(1, 2, 3, 4) {'d': 'D'}
<class '__main__.D'>
(1, 2, 3, 4)
{'d': 'D'}
'{'a1': 1, 'a2': 2, 'Problem': 'B'}'
此解决方案不起作用,因为我也想存储args名称 当前版本影响的ex: 声明:
class A:
def __init__(self, x):
self.x = x
class B(A):
@init_store
def __init__(self, a1, a2):
self.a1, self.a2 = a1, a2
super(B, self).__init__(True)
电话:
b = B(1, 2)
print(b.init_values)
输出:
(1, 2, 3) {'a': 'A', 'b': 'B'}
<class '__main__.C'>
(1, 2, 3)
{'a': 'A', 'b': 'B'}
(1, 2, 3, 4) {'d': 'D'}
<class '__main__.D'>
(1, 2, 3, 4)
{'d': 'D'}
'{'a1': 1, 'a2': 2, 'Problem': 'B'}'
如果您将类设计为只使用关键字参数,这似乎会简单得多;然后,您只需要子类将其所有参数传递给
super()。\uuuuu init\uuuuu
,您的基类\uuuuuuuu init\uuuuuu
就可以简单地保存**kwargs
,而无需修饰任何方法。是的,这种方法非常有效,但我更愿意不必将我的类更改为只使用kwargsWhy<如果不必考虑参数传递给各种方法的顺序,则代码>超级更容易正确使用。主类只有一个,但每个子类可能会引入冲突的位置参数。关键字参数标识它们自己,并且不依赖于它们的传递顺序。@vjhjj请参见我的编辑。如果您开始有子类引入它们自己的位置参数,则使用位置参数会变得混乱。假设A
有一个参数,B
和C
各自继承自A
并添加自己的第二个参数,然后D
继承自B
和C
。如何解释D(1,2,3)
?我没有这个问题,因为super的唯一参数取决于我所处的子类,而不是在创建子类实例时使用的参数sublcass init看起来像:``def uu init uu(self,*args):`Use args super()。`uu_uinit uu(True)```@chepner,你是对的,你的评论“主类只有一个,但是……”使你的观点非常清楚。我只是没有得到这一切的行动意图。我看你的例子很简单。具有这些位置的D实例。你想对他们做什么就做什么。把它们传给super时也是一样。是的,这太傻了。它意味着一个类知道它在层次结构中的位置以选择合适的参数。这就把这些课程和太多的知识联系起来了。我从来不需要写这样的代码(但那只是我自己),这就是为什么我没有考虑太多。我正在编辑我的答案。如果你想存储arg名称,你是说你需要在实例创建调用中使用关键字args。