Python实现泛型序列化时如何初始化指定泛型类型的实体对象?
问题核心原因
Python的泛型参数仅用于静态类型检查,运行时会被完全擦除,无法像C#那样直接通过泛型参数T获取到实际类型构造实例,必须显式关联序列化实体类才能解决该问题。同时你原有代码中用re.finditer匹配分隔符的逻辑存在错误,拿到的是分隔符本身而非拆分后的业务内容,也需要同步修正。
修正实现方案
核心思路是给SerializableList增加element_type类属性,用于绑定对应泛型的实际实体类,反序列化时直接调用该属性的from_str方法构造实例即可。
完整修正代码
from typing import TypeVar, List, Type, Generic # 给TypeVar加边界约束,仅允许Serializable的子类作为泛型参数 T = TypeVar('T', bound='Serializable') class Serializable(Generic[T]): def to_str(self) -> str: raise NotImplementedError @classmethod def from_str(cls, content: str) -> T: raise NotImplementedError class SerializableList(Generic[T], List[T]): # 子类继承时可直接覆盖这两个类属性,无需重复实现初始化逻辑 element_type: Type[T] = None separator: str = "\n" @classmethod def from_str(cls, content: str) -> "SerializableList[T]": if not cls.element_type: raise ValueError("请先指定element_type为对应序列化实体类") instance = cls() # 按分隔符拆分内容,过滤空字符串 for item_str in content.split(cls.separator): item_str = item_str.strip() if not item_str: continue # 直接用绑定的实体类构造实例 instance.append(cls.element_type.from_str(item_str)) return instance def to_str(self) -> str: return self.separator.join([e.to_str() for e in self]) + self.separator
用法演示
方式1:继承基类实现固定类型的序列化列表
# 1. 实现具体的实体序列化类 class User(Serializable['User']): def __init__(self, name: str, age: int): self.name = name self.age = age def to_str(self) -> str: return f"{self.name},{self.age}" @classmethod def from_str(cls, content: str) -> 'User': name, age = content.split(',') return cls(name, int(age)) # 2. 实现对应类型的列表序列化类 class UserList(SerializableList[User]): # 绑定泛型对应的实际实体类 element_type = User # 可自定义分隔符,默认是\n # separator = "|"
测试效果
# 序列化测试 user1 = User("张三", 20) user2 = User("李四", 25) user_list = UserList() user_list.extend([user1, user2]) serialized_str = user_list.to_str() print(serialized_str) # 输出: # 张三,20 # 李四,25 # 反序列化测试 deserialized_list = UserList.from_str(serialized_str) print(deserialized_list[0].name) # 输出 张三 print(deserialized_list[1].age) # 输出 25
方式2:动态创建序列化列表(无需单独写子类)
如果不需要复用列表类,可以用工厂方法动态生成对应类型的序列化列表:
def create_serializable_list(element_type: Type[T], separator: str = "\n") -> Type[SerializableList[T]]: class DynamicSerializableList(SerializableList[T]): element_type = element_type separator = separator return DynamicSerializableList # 动态生成User列表类,和上面继承方式效果完全一致 UserList = create_serializable_list(User)
内容的提问来源于stack exchange,提问作者TWP
相关产品推荐
相关产品推荐

