将图书信息XML转JSON时遇json serialization错误求助
解决XML转JSON时的"cannot handle a sequence of length 3"错误
嘿,这个错误我之前帮不少开发者排查过,本质是XML到JSON的结构映射出了问题——咱们一步步来拆解解决:
先搞懂错误含义
这个报错的核心是:你的XML里存在某个节点包含了3个同类型的子元素(也就是所谓的"长度为3的序列"),而你用的JSON序列化工具默认不知道该怎么处理这种结构。比如某本书的<author>节点出现了3次,工具默认以为author是单个字符串值,突然遇到多个就懵了,直接抛出错误。
具体解决步骤
1. 先检查你的XML结构
先打开biblio.xml,找一找有没有重复出现3次的节点(大概率是<author>)。比如你的XML可能类似这样:
<books> <book> <author>W. Stevens</author> <title>TCP/IP Illustrated</title> <year>1994</year> </book> <book> <author>W. Stevens</author> <author>G. Wright</author> <author>A. Fenner</author> <!-- 这里3个author就是触发错误的原因 --> <title>TCP/IP Illustrated Volume 2</title> <year>1995</year> </book> </books>
2. 用工具强制指定数组映射
针对这种情况,我们需要告诉序列化工具:不管某个节点有几个子元素,都把它转成JSON数组。这里推荐两种常用方案:
方案一:用Python的xmltodict库(简单易上手)
安装库后,通过force_list参数指定<author>必须转成数组:
import xmltodict import json # 读取XML文件 with open('biblio.xml', 'r', encoding='utf-8') as f: xml_content = f.read() # 强制将author节点转为数组,哪怕只有一个作者 parsed_dict = xmltodict.parse(xml_content, force_list={'author'}) # 提取book列表并转成JSON result_json = json.dumps(parsed_dict['books']['book'], indent=2) # 输出或保存结果 print(result_json) with open('biblio.json', 'w', encoding='utf-8') as f: f.write(result_json)
执行后就能得到你想要的格式:每个book对象的author都是数组,不管作者数量多少。
方案二:用命令行工具xmlstarlet(适合无代码场景)
先写一个XSLT转换规则文件biblio.xslt,明确定义XML到JSON的映射逻辑:
<xsl:stylesheet version="1.0" xmlns:xsl="http://www.w3.org/1999/XSL/Transform"> <xsl:output method="json" indent="yes"/> <xsl:template match="/books"> <xsl:text>[</xsl:text> <!-- 遍历每本书 --> <xsl:for-each select="book"> <xsl:if test="position() > 1">,</xsl:if> <xsl:text>{</xsl:text> <!-- 处理author数组 --> <xsl:text>"author": [</xsl:text> <xsl:for-each select="author"> <xsl:if test="position() > 1">,</xsl:if> <xsl:text>"</xsl:text><xsl:value-of select="."/><xsl:text>"</xsl:text> </xsl:for-each> <xsl:text>],</xsl:text> <!-- 处理title和year --> <xsl:text>"title": "</xsl:text><xsl:value-of select="title"/><xsl:text>",</xsl:text> <xsl:text>"year": "</xsl:text><xsl:value-of select="year"/><xsl:text>"</xsl:text> <xsl:text>}</xsl:text> </xsl:for-each> <xsl:text>]</xsl:text> </xsl:template> </xsl:stylesheet>
然后执行命令完成转换:
xmlstarlet transform biblio.xslt biblio.xml
3. 验证结果
转换完成后,检查输出的JSON是否符合你的预期:
[ { "author": [ "W. Stevens" ], "title": "TCP/IP Illustrated", "year": "1994" }, { "author": [ "W. Stevens", "G. Wright", "A. Fenner" ], "title": "TCP/IP Illustrated Volume 2", "year": "1995" } ]
内容的提问来源于stack exchange,提问作者Begoña Sustatxa
相关产品推荐
相关产品推荐

