如何在lxml中同时实现XML美观打印且避免空元素转为自闭合标签
如何在lxml中同时实现XML美观打印且避免空元素转为自闭合标签
这个问题我之前处理XML的时候也碰到过,确实有点头疼——lxml的美观打印和保留非自闭合的空标签好像天生有点“拧巴”,不过咱们可以通过两个实用的思路解决它:
方法一:手动处理空元素,强制保留展开标签
核心思路是:先用remove_blank_text=True的解析器保证后续能正确格式化XML,处理完节点移除操作后,遍历所有元素,给空元素添加一个空白文本节点,让lxml认为它不是完全空的,从而不会转成自闭合标签。
完整代码示例:
import lxml.etree # 启用空白文本移除的解析器,为后续美观打印做准备 xml_parser = lxml.etree.XMLParser(remove_blank_text=True) xml_tree = lxml.etree.parse("myFile.xml", xml_parser) root = xml_tree.getroot() # 你的节点移除逻辑(用list()避免遍历过程中修改节点引发的问题) for fruit in root: if fruit.tag == "apple": for apple in list(fruit): if apple.tag == "McIntosh": fruit.remove(apple) # 递归遍历所有元素,处理空元素 def keep_non_self_closing(element): # 如果元素没有子节点且没有文本内容,添加空白文本节点 if len(element) == 0 and element.text is None: element.text = '' # 递归处理子元素 for child in element: keep_non_self_closing(child) keep_non_self_closing(root) # 写入文件,启用美观打印 tree = lxml.etree.ElementTree(root) tree.write( "output.xml", pretty_print=True, xml_declaration=True, encoding="utf-8" )
运行后你会得到格式整齐的XML,同时<apple>会保留<apple></apple>的形式,不会变成自闭合标签。
方法二:用HTML写入模式强制所有标签非自闭合
如果你不介意所有自闭合标签都被展开(比如原来的<McIntosh/>会变成<McIntosh></McIntosh>),可以直接在写入时加上method='html'参数,这样lxml会按照HTML的规则输出标签,不会生成自闭合形式:
tree.write( "output.xml", pretty_print=True, xml_declaration=True, encoding="utf-8", method='html' )
这种方法更简单,但灵活性差一些,适合不需要区分自闭合/非自闭合标签的场景。
备注:内容来源于stack exchange,提问作者Autechre
相关产品推荐
相关产品推荐

