Pydantic模型中typing.Optional[]两种定义方式的区别解析
关于Pydantic中
typing.Optional[]隐式与显式赋值None的技术区别 在Pydantic模型定义时,a: typing.Optional[int](隐式声明可选)和a: typing.Optional[int] = None(显式指定默认值为None)两种写法,实例化后字段最终值都是None,但二者存在以下技术差异:
示例代码
import typing import pydantic class Bar(pydantic.BaseModel): a: typing.Optional[int] @pydantic.validator('a', always=True, pre=True) def check_a(cls, v, values, field): print("WITHOUT NONE") print(values) print(field) return v class Baz(pydantic.BaseModel): a: typing.Optional[int] = None @pydantic.validator('a', always=True, pre=True) def check_a(cls, v, values, field): print("WITH NONE") print(values) print(field) return v print(Bar()) print(Baz())
输出结果
WITHOUT NONE {} name='a' type=Optional[int] required=False default=None a=None WITH NONE {} name='a' type=Optional[int] required=False default=None a=None
具体技术差异
默认值的来源不同
隐式写法里,Optional仅标记字段类型允许为None,字段的默认值None是Pydantic基于类型规则自动补充的;显式写法则是开发者主动为字段指定默认值为None。从输出的field信息能看到两者最终都有default=None,但底层逻辑上一个是框架自动推断,一个是开发者显式声明。复杂场景下的行为差异
比如使用exclude_unset参数序列化模型时:隐式声明的可选字段如果从未被赋值,在部分Pydantic版本中会被排除在序列化结果外;而显式赋值None的字段,即使没被修改,也会被视为“已设置”,会出现在序列化结果中。另外在模型继承、结合Field函数自定义字段规则时,显式默认值的优先级会高于框架自动补充的默认值。语义表达的清晰度不同
隐式写法侧重表达“字段类型可选,可接受None”;显式写法除了说明类型可选,还明确告知“字段默认值就是None”,在团队协作中更清晰,能减少对字段默认行为的歧义理解。
内容的提问来源于stack exchange,提问作者Hichem Dridi
相关产品推荐
相关产品推荐

