<h2>使用<code>csv.DictWriter</code>,从<code>node.attrib</code>字典中获取值</h2>
<p>名为<code>TrdCapRpt</code>的元素具有属性,如果有这样的节点,则其属性<code>node.attrib</code>
保存包含每个属性的键/值的字典。在</p>
<p><code>csv.DictWriter</code>允许写入字典中的数据。在</p>
<p>首先是一些导入(我总是使用<code>lxml</code>,因为它非常快,并且提供了额外的功能):</p>
<pre><code>from lxml import etree
import csv
</code></pre>
<p>配置要在每个记录中使用的文件名和字段:</p>
^{pr2}$
<p>阅读XML:</p>
<pre><code>xml = etree.parse(xml_fname)
</code></pre>
<p>迭代元素“TrdCapRpt”,将属性值写入CSV文件:</p>
<pre><code>with open(csv_fname, "w") as f:
writer = csv.DictWriter(f, fields, delimiter=";", extrasaction="ignore")
writer.writeheader()
for node in xml.iter("TrdCaptRpt"):
writer.writerow(node.attrib)
</code></pre>
<p>如果您喜欢使用stdlib <code>xml.etree.ElementTree</code>,那么您应该像现在这样轻松地管理,因为{<cd2>}也在那里。在</p>
<h2>从多个元素名称读取</h2>
<p>在您的评论中,您注意到,您希望从more导出属性
元素名称。这也是可能的。为此,我将示例修改为
使用<code>xpath</code>(这可能只适用于<code>lxml</code>)并添加额外的列
<code>"elm_name"</code>要跟踪,从哪个元素创建记录:</p>
<pre><code>fields = [
"elm_name",
"RptID", "TrdTyp", "TrdSubTyp", "ExecID", "TrdDt", "BizDt", "MLegRptTyp",
"MtchStat" "MsgEvtSrc", "TrdID", "LastQty", "LastPx", "TxnTm", "SettlCcy",
"SettlDt", "PxSubTyp", "VenueTyp", "VenuTyp", "OfstInst",
"Typ", "Amt", "Ccy"
]
xml = etree.parse(xml_fname)
with open(csv_fname, "w") as f:
writer = csv.DictWriter(f, fields, delimiter=";", extrasaction="ignore")
writer.writeheader()
for node in xml.xpath("//*[self::TrdCaptRpt or self::PosRpt or self::Amt]"):
atts = node.attrib
atts["elm_name"] = node.tag
writer.writerow(node.attrib)
</code></pre>
<p>修改内容包括:</p>
<ul>
<li><code>fields</code>得到了额外的<code>"elm_name"</code>字段和其他元素的字段(请随意删除那些您不感兴趣的)。在</li>
<li>使用<code>xml.xpath</code>迭代元素。XPath表达式更复杂,所以我不确定stdlib ElementTree是否支持它。在</li>
<li>在编写记录之前,我将元素的名称添加到<code>atts</code>字典中以提供元素的名称。在</li>
</ul>
<p>警告:元素<code>Amt</code>嵌套在<code>PosRpt</code>和这个树结构中
无法在CSV中支持。记录是写下来的,但不成立
关于他们来自哪里的信息(除了跟踪记录
父元素)。在</p>