我想做一个QAbstractItemModel
从一系列 Xml 文件中获取数据的文件,所有文件都位于同一目录中。由于 PyQt5 不再支持QDomDocument
(或者至少我找不到让它工作的方法),我不得不求助于QXmlStreamReader
. 我将数据本身放在一个巨大的 python 字典中(嗯......不完全是计算机科学标准的巨大),其中包含各种键下的其他字典以创建树状结构。
到目前为止,这是我的代码:
class DataModel(QtCore.QAbstractItemModel):
def __init__(self, settingsDirectory, parent = None):
super(DataModel, self).__init__(parent)
settingsDirectory.setNameFilters(["*.xml"])
files = settingsDirectory.entryList()
print(files)
self.data = {}
for i in range(len(files)):
filePath = str(files[i])
file = QtCore.QFile(settingsDirectory.absolutePath() + "/" + str(filePath))
fileOpens = file.open(file.ReadOnly | file.Text)
if fileOpens:
parser = QtCore.QXmlStreamReader(file)
print("--------Beginning parsing----------")
print("Reading file: "+str(filePath))
while not parser.atEnd():
parser.readNext()
token = parser.tokenType()
print("Reading tag: " + str(parser.name()))
print("Tag type is: " + str(token))
if token == parser.StartDocument:
self.data["XML Version"] = str(parser.documentVersion())
self.data["XML Encoding"] = str(parser.documentEncoding())
if token == parser.StartElement:
tokenName = parser.name()
if parser.tokenType() == parser.Characters:
tokenText = parser.text()
print("This tag has a text value: " + str(tokenText))
print("current data: " + str(self.data))
if token == parser.EndElement:
if tokenText != None:
self.data[tokenName] = tokenText
else:
self.data[tokenName] = {}
tokenName = None
tokenText = None
else:
print(self.tr("xml file did not open properly"))
print(self.data)
虽然这段代码没有崩溃或任何事情,但它确实有一些我不知道为什么会发生或如何修复的问题:
1.由于某种原因tokenName
永远不会改变- 已解决None
2.self.data
字典的结构没有变成树状的,不知道为什么:|
示例数据:
<?xml version="1.0" encoding="UTF-8"?>
<tag>
<description>This is a text</description>
<types>
<typesAllowed></typesAllowed>
<typesEnabled></typesEnabled>
</types>
</tag>
产生最终结果:
{'XML Encoding': 'UTF-8', 'XML Version': '1.0', 'typesAllowed': '\n\t\t', None: '\n', 'typesEnabled': '\n\t\t', 'description': 'This is a text'}
而不是想要的:
{'XML Encoding': 'UTF-8', 'XML Version': '1.0', 'tag': {'description': 'this is a text', typesAllowed': '\n\t\t', 'typesEnabled': '\n\t\t'}}
我知道这些问题很可能是由于我对 a 的工作原理了解不足StreamReader
,因此欢迎提供任何和所有提示 :)
编辑1:
tokenName
改变是一个愚蠢的定位错误,我很傻。代码反映了修复。
编辑2:
添加了示例和示例输出