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

Python子类无法获取父类私有属性问题求助

问题分析与解决

你的问题出在Python的**名称改写(Name Mangling)**机制上。当类中定义以双下划线__开头的属性时,Python会自动将其重命名为_类名__属性名,目的是防止子类意外覆盖父类的私有属性。

报错原因

  • 父类Queue里的self.__queue_list会被Python悄悄改写为self._Queue__queue_list
  • 你在子类SuperQueue里写Queue.__queue_list,是试图访问Queue类的类属性,而非实例属性,自然找不到
  • 如果写self.__queue_list,Python会去寻找self._SuperQueue__queue_list,但这个属性从未被初始化,所以同样报错

解决方法(三种可选)

方法1:将父类属性改为保护属性(单下划线)

把父类的__queue_list改成_queue_list,单下划线表示这是“保护属性”,子类可访问但不建议随意修改:

class QueueError(Exception):
    pass

class Queue:
    def __init__(self):
        self._queue_list = []  # 单下划线标识保护属性

    def put(self, val):
        self._queue_list.insert(0, val)

    def get(self):
        if len(self._queue_list) == 0:
            raise QueueError
        else:
            val = self._queue_list[-1]
            del self._queue_list[-1]
            return val

class SuperQueue(Queue):
    def __init__(self):
        super().__init__()  # 用super()调用父类初始化更简洁

    def isempty(self):
        return len(self._queue_list) == 0

方法2:在子类中使用改写后的属性名

直接用Python改写后的名称访问父类私有属性(不推荐,破坏封装性):

class QueueError(Exception):
    pass

class Queue:
    def __init__(self):
        self.__queue_list = []

    def put(self, val):
        self.__queue_list.insert(0, val)

    def get(self):
        if len(self.__queue_list) == 0:
            raise QueueError
        else:
            val = self.__queue_list[-1]
            del self.__queue_list[-1]
            return val

class SuperQueue(Queue):
    def __init__(self):
        super().__init__()

    def isempty(self):
        return len(self._Queue__queue_list) == 0  # 使用改写后的属性名

方法3:在父类中添加状态查询方法(推荐)

最符合面向对象封装原则的方式,父类提供方法暴露状态,子类无需直接访问内部属性:

class QueueError(Exception):
    pass

class Queue:
    def __init__(self):
        self.__queue_list = []

    def put(self, val):
        self.__queue_list.insert(0, val)

    def get(self):
        if len(self.__queue_list) == 0:
            raise QueueError
        else:
            val = self.__queue_list[-1]
            del self.__queue_list[-1]
            return val

    def is_empty(self):  # 父类新增状态查询方法
        return len(self.__queue_list) == 0

class SuperQueue(Queue):
    def __init__(self):
        super().__init__()

    def isempty(self):
        return self.is_empty()  # 调用父类方法获取状态

修改后运行测试代码,会得到正确输出:

1
dog
False
Queue empty

内容的提问来源于stack exchange,提问作者Oscar Castro

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.06.22 08:12:43