Python数据类继承疑问:super()使用是否正确?参数传递问题
Python Dataclass继承与super()使用问题解析
你的代码核心问题在于手动重写__init__破坏了dataclass的自动生成逻辑,导致参数传递完全混乱,具体问题和修复方案如下:
错误点分析
- 父类必填字段未处理:
ZooAnimals中的food_daily_kg和price_food是无默认值的必填字段,但Cats的__init__完全没接收这两个参数,调用super().__init__时位置参数被错误映射到父类字段(比如你传的[30]被当成food_daily_kg,name='Leopard'被当成price_food,这就是输出字段混乱的原因)。 - 没必要手动重写
__init__:dataclass会自动处理继承字段,生成包含所有父类字段的__init__方法,手动重写反而打乱了这个逻辑。 - super()调用参数错误:混用位置参数和关键字参数,且参数顺序与父类自动生成的
__init__不匹配,导致字段赋值完全错位。 - __post_init__的小错误:
weight是InitVar类型,不会成为实例属性,不能通过self.weight访问,只能用__post_init__的参数接收。
正确实现方式
如果Cats类没有新增字段,仅继承父类即可,无需额外方法:
from typing import Optional from dataclasses import dataclass, field, InitVar @dataclass class ZooAnimals(): myrange = list(range(10, 16, 1)) food_daily_kg: Optional[int] price_food: float area_required: list = field(default_factory=list) name: str = field(default='Zebra', kw_only=True) weight: InitVar[int] = field(default = 50, kw_only=True) weight_pounds: int = field(init=False) dangerous_animal_warning: str = field(default='No', kw_only=True, init=False) def __post_init__(self, weight): # 用__post_init__的参数weight,而非self.weight self.weight_pounds = weight * 2.7 if self.name == 'Crocodile': self.dangerous_animal_warning = "Dangerous" @dataclass class Cats(ZooAnimals): # 无需重写__init__,dataclass自动生成包含所有父类字段的构造方法 pass # 实例化必须传入父类必填字段food_daily_kg和price_food z = Cats(food_daily_kg=3, price_food=12.5, area_required=[30], name='Leopard', weight=35) print(z) # 输出:Cats(food_daily_kg=3, price_food=12.5, area_required=[30], name='Leopard', weight_pounds=94.5, dangerous_animal_warning='No')
扩展初始化逻辑的正确做法
如果需要给Cats添加特有的初始化逻辑,应该重写__post_init__并调用父类的对应方法,而非重写__init__:
@dataclass class Cats(ZooAnimals): def __post_init__(self, weight): super().__post_init__(weight) # 这里添加Cats专属的初始化逻辑 print(f"{self.name} is a cat!")
内容的提问来源于stack exchange,提问作者user4718221
相关产品推荐
相关产品推荐

