使用kw_only的Dataclass继承时super调用触发TypeError问题排查
问题:dataclass开启kw_only后调用super().__init__报错
我正在练习super函数与dataclass继承,为父类含默认值的场景开启了kw_only属性。我清楚仅传递变量时dataclass无需手动调用super,但为深入理解super特性编写了示例,却遇到了错误。
代码示例
from dataclasses import dataclass @dataclass(kw_only=True) class ZooAnimals(): food_daily_kg: int price_food: float area_required: float name: str c = ZooAnimals(food_daily_kg=565, price_food=40, area_required=10, name='Monkey') print(c) @dataclass(kw_only=True) class Cats(ZooAnimals): meowing: str def __init__(self, food_daily_kg, price_food, area_required, meowing, name): self.meowing = meowing super().__init__(food_daily_kg, price_food, area_required, name) z = Cats(food_daily_kg=465, price_food=30, area_required=10, meowing='Little Bit', name='Leopard') print(z)
错误输出
ZooAnimals(food_daily_kg=565, price_food=40, area_required=10, name='Monkey') TypeError: ZooAnimals.__init__() takes 1 positional argument but 5 were given
原因分析
当给dataclass添加kw_only=True参数时,自动生成的__init__方法只接受关键字参数,不允许使用位置参数传值。你在Cats的自定义__init__里用位置参数调用super().__init__,直接违反了这个限制,所以触发了TypeError。
解决方法
方法1:改用关键字参数调用父类构造方法
修改Cats类里的super().__init__调用,把位置参数改成关键字参数:
@dataclass(kw_only=True) class Cats(ZooAnimals): meowing: str def __init__(self, food_daily_kg, price_food, area_required, meowing, name): self.meowing = meowing # 用关键字参数传递父类字段 super().__init__( food_daily_kg=food_daily_kg, price_food=price_food, area_required=area_required, name=name )
方法2:放弃手动写__init__,让dataclass自动处理
dataclass本身支持继承场景下的字段自动合并,加上kw_only=True后,子类的字段也会默认是关键字参数,完全不需要手动实现__init__:
@dataclass(kw_only=True) class Cats(ZooAnimals): meowing: str # 直接按关键字参数实例化即可 z = Cats(food_daily_kg=465, price_food=30, area_required=10, meowing='Little Bit', name='Leopard') print(z) # 输出:Cats(food_daily_kg=465, price_food=30, area_required=10, name='Leopard', meowing='Little Bit')
内容的提问来源于stack exchange,提问作者user4718221
相关产品推荐
相关产品推荐

