Python超类__init__方法未被称为

时间:2017-05-12 16:35:40

标签: python python-3.x

当我在Python 3.6中运行以下程序时:

import xml.etree.ElementTree

def startElementHandler(name, attributes):
    print("Name:", name)

class Parser(xml.etree.ElementTree.XMLParser):
    def __init__(self, html=0, target=None, encoding=None):
        super(Parser, self).__init__(html, target, encoding)
        self.parser.StartElementHandler = startElementHandler

if __name__ == "__main__":
    parser = Parser()
    print("Success")

我得到以下堆栈跟踪:

Traceback (most recent call last):
  File "D:\src\python\base_init\base_init.py", line 12, in <module>
    parser = Parser()
  File "D:\src\python\base_init\base_init.py", line 9, in __init__
    self.parser.StartElementHandler = startElementHandler
AttributeError: 'Parser' object has no attribute 'parser'

正如您在XMLParser class source code中所看到的那样,我使用正确的参数调用其__init__()方法,并在其中设置XMLParser的{​​{1}}属性。

发生的事情是parser方法没有被调用。我究竟做错了什么?它一定是傻事,但我看不到它。

3 个答案:

答案 0 :(得分:1)

XMLParser的C加速器that's imported没有设置parser属性。一个可行的选项是通过在None中将其设置为sys.modules来禁用它的导入:

import sys
sys.modules['_elementtree'] = None

当然,为了实现这一点,需要在之前完成 ElementTree的任何导入,显然,您会受到性能影响。< / p>

至于为什么这是,我猜测parser属性被认为是XMLParser的私有API的一部分,不存在任何文档(和它看起来不像是一个遗漏)。因此,不应该依赖它。

答案 1 :(得分:0)

对于python 2.X,你的代码很好但是对于python 3.x你必须改变这个

self.parser.StartElementHandler = startElementHandlerself.StartElementHandler = startElementHandler

import xml.etree.ElementTree

def startElementHandler(name, attributes):
    print("Name:", name)

class Parser(xml.etree.ElementTree.XMLParser):
    def __init__(self, html=0, target=None, encoding=None):
        super(Parser, self).__init__(html, target, encoding)
        self.StartElementHandler = startElementHandler

if __name__ == "__main__":
    parser = Parser()
    print("Success")

答案 2 :(得分:0)

如果您只想打印起始元素的标记名称,可以使用不需要修补解析器对象的xml.etree.ElementTree.iterparse

import xml.etree.ElementTree

for event, elem in xml.etree.ElementTree.iterparse(filepath, events=['start']):
    print('Name:', elem.tag)
  • filepath可以是xml文件路径或类似文件的对象。