XML 漂亮的打印在 Python lxml 中失败
XML pretty print fails in Python lxml
我正在尝试在 Python 2.7.6.
中使用 lxml 4.1.1 读取、修改和写入 XML 文件
我的代码:
import lxml.etree as et
fn_xml_in = 'in.xml'
parser = et.XMLParser(remove_blank_text=True)
xml_doc = et.parse(fn_xml_in, parser)
xml_doc.getroot().find('b').append(et.Element('c'))
xml_doc.write('out.xml', method='html', pretty_print=True)
输入文件 in.xml
如下所示:
<a>
<b/>
</a>
以及生成的输出文件out.xml
:
<a>
<b><c></c></b>
</a>
或者当我设置 remove_blank_text=True
:
<a><b><c></c></b></a>
我原以为 lxml 会在 b
元素中插入换行符和缩进:
<a>
<b>
<c></c>
</b>
</a>
我怎样才能做到这一点?
我尝试了一些 tidy
库包装器,但它们似乎专注于 HTML 而不是 XML。
我也尝试过添加换行符作为 b
的 tail
,但是连缩进都被破坏了。
编辑: 我需要 c
元素在开始和结束标记中保持分隔:<c></c>
。这就是我在示例中使用 method='HTML'
的原因。
感谢 mzjn 的评论,我找到了一个可行但不优雅的解决方案。由于我需要空元素保留在 HTML 语法中,因此仅使用 method='XML'
并不令人满意。
两次格式化文档会产生所需的结果:
import lxml.etree as et
parser = et.XMLParser(remove_blank_text=True)
xml_doc = et.parse('in.xml', parser)
xml_doc.getroot().find('b').append(et.Element('c'))
xml_doc.write('out.xml', pretty_print=True)
parser = et.XMLParser(remove_blank_text=False)
xml_doc = et.parse('out.xml', parser)
xml_doc.write('out.xml', pretty_print=True, method='HTML')
结果:
<a>
<b>
<c></c>
</b>
</a>
不优雅,但工作。
写入时使用"xml"输出方法(这是默认的,所以不必明确给出)。
将 c
元素的 text
属性 设置为空字符串,以确保该元素被序列化为 <c></c>
。
代码:
import lxml.etree as et
parser = et.XMLParser(remove_blank_text=True)
xml_doc = et.parse('in.xml', parser)
b = xml_doc.getroot().find('b')
c = et.Element('c')
c.text=''
b.append(c)
xml_doc.write('out.xml', pretty_print=True)
结果(out.xml):
<a>
<b>
<c></c>
</b>
</a>
我正在尝试在 Python 2.7.6.
中使用 lxml 4.1.1 读取、修改和写入 XML 文件我的代码:
import lxml.etree as et
fn_xml_in = 'in.xml'
parser = et.XMLParser(remove_blank_text=True)
xml_doc = et.parse(fn_xml_in, parser)
xml_doc.getroot().find('b').append(et.Element('c'))
xml_doc.write('out.xml', method='html', pretty_print=True)
输入文件 in.xml
如下所示:
<a>
<b/>
</a>
以及生成的输出文件out.xml
:
<a>
<b><c></c></b>
</a>
或者当我设置 remove_blank_text=True
:
<a><b><c></c></b></a>
我原以为 lxml 会在 b
元素中插入换行符和缩进:
<a>
<b>
<c></c>
</b>
</a>
我怎样才能做到这一点?
我尝试了一些 tidy
库包装器,但它们似乎专注于 HTML 而不是 XML。
我也尝试过添加换行符作为 b
的 tail
,但是连缩进都被破坏了。
编辑: 我需要 c
元素在开始和结束标记中保持分隔:<c></c>
。这就是我在示例中使用 method='HTML'
的原因。
感谢 mzjn 的评论,我找到了一个可行但不优雅的解决方案。由于我需要空元素保留在 HTML 语法中,因此仅使用 method='XML'
并不令人满意。
两次格式化文档会产生所需的结果:
import lxml.etree as et
parser = et.XMLParser(remove_blank_text=True)
xml_doc = et.parse('in.xml', parser)
xml_doc.getroot().find('b').append(et.Element('c'))
xml_doc.write('out.xml', pretty_print=True)
parser = et.XMLParser(remove_blank_text=False)
xml_doc = et.parse('out.xml', parser)
xml_doc.write('out.xml', pretty_print=True, method='HTML')
结果:
<a>
<b>
<c></c>
</b>
</a>
不优雅,但工作。
写入时使用"xml"输出方法(这是默认的,所以不必明确给出)。
将 c
元素的 text
属性 设置为空字符串,以确保该元素被序列化为 <c></c>
。
代码:
import lxml.etree as et
parser = et.XMLParser(remove_blank_text=True)
xml_doc = et.parse('in.xml', parser)
b = xml_doc.getroot().find('b')
c = et.Element('c')
c.text=''
b.append(c)
xml_doc.write('out.xml', pretty_print=True)
结果(out.xml):
<a>
<b>
<c></c>
</b>
</a>