You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

如何创建可通过自身实例初始化的Python类

实现支持自身实例初始化的类

要实现既能用原始数据初始化,又能用自身实例初始化的类,核心是在实例创建/初始化阶段判断输入参数类型,针对性处理。下面分两种场景给出实现方案:

方案1:返回原实例(满足instance2 is instance1)

如果需要直接复用传入的实例(新创建对象与传入实例为同一个引用),需重写类的__new__方法——它负责创建实例对象:

from typing import Mapping, Union


class NewClass:
    """支持用映射类型或自身实例初始化的类"""
    def __new__(cls, obj: Union[Mapping, 'NewClass']):
        # 若传入自身实例,直接返回该实例
        if isinstance(obj, cls):
            return obj
        # 否则创建新实例
        return super().__new__(cls)

    def __init__(self, data: Union[Mapping, 'NewClass']):
        # 仅当输入不是自身实例时,执行初始化逻辑
        if not isinstance(data, type(self)):
            self.data = data

    def cool_method(self):
        assert isinstance(self.data, Mapping)
        # 示例业务逻辑:返回data的键列表
        return list(self.data.keys())

验证最简示例

arg = {"name": "test", "value": 123}
instance1 = NewClass(arg)
instance2 = NewClass(instance1)
assert instance2 is instance1  # 断言成立,返回同一实例
assert instance2.data == instance1.data  # 数据完全一致

适配复杂示例中的AnotherClass

class AnotherClass:
    """接受映射类型或NewClass实例,内部使用NewClass"""
    def __init__(self, obj: Union[Mapping, NewClass]):
        # 传入NewClass实例时,直接复用原实例,避免重复初始化
        self.cool = NewClass(obj).cool_method()

方案2:创建新实例但属性一致(满足instance2 == instance1)

若不需要复用同一实例,仅要求新实例属性与传入实例一致,可仅在__init__中处理:

from typing import Mapping, Union


class NewClass:
    def __init__(self, data: Union[Mapping, 'NewClass']):
        if isinstance(data, type(self)):
            # 复制传入实例的属性(用copy避免原数据被意外修改)
            self.data = data.data.copy()
        else:
            self.data = data

    def __eq__(self, other):
        # 定义相等判断逻辑,满足instance2 == instance1
        if isinstance(other, type(self)):
            return self.data == other.data
        return False

    def cool_method(self):
        assert isinstance(self.data, Mapping)
        return list(self.data.keys())

验证示例

arg = {"name": "test", "value": 123}
instance1 = NewClass(arg)
instance2 = NewClass(instance1)
assert instance2 == instance1  # 断言成立
assert instance2 is not instance1  # 为不同实例

关键要点

  • 类型标注:用Union[Mapping, 'NewClass']支持两种输入类型,'NewClass'是字符串形式的前向引用,避免类未定义时的报错。
  • 实例判断:通过isinstance(obj, cls)或isinstance(data, type(self))识别自身实例。
  • 复用实例场景:必须重写__new__,因为__init__无法返回新实例,只能初始化已创建的实例。

内容的提问来源于stack exchange,提问作者Nikolay Prokopyev

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.08.01 01:15:32