You need to enable JavaScript to run this app.
最新活动
大模型
产品
解决方案
定价
生态与合作
支持与服务
开发者
了解我们

在C#中使用XmlDocument修改XML文件时XmlNodeList查询为空的问题排查

问题分析与解决方案

你遇到的核心问题有两个:一是代码里的XmlDocument.Load调用方式有误,二是XML文档包含命名空间,但你的XPath查询没有处理命名空间,这才是节点始终匹配不到的关键原因。

1. 修正XmlDocument.Load的调用方式

先看你代码里的这部分:

XmlDocument xml = new XmlDocument(); 
xml = xml.Load(@"https://www.aade.gr/...xml"); 

XmlDocument.Load()是一个无返回值的void方法,它不会生成新的XmlDocument对象,所以这里的赋值操作是错误的。正确写法应该是直接调用:

XmlDocument xml = new XmlDocument(); 
xml.Load(@"https://www.aade.gr/...xml"); // 去掉多余的赋值

虽然你说保存后能看到XML内容,可能实际代码里已经修正了这个问题,但这是需要注意的语法细节。

2. 处理XML命名空间(核心解决点)

你要修改的XML文档带有默认命名空间(比如根节点会有类似xmlns="http://www.aade.gr/myDATA/invoice/v1.0"的声明),而XPath默认不会识别默认命名空间,必须通过XmlNamespaceManager绑定命名空间前缀,才能正确匹配节点。

完整修正代码

XmlDocument xml = new XmlDocument();
xml.Load(@"https://www.aade.gr/sites/default/files/2020-09/SampleXML_1.1%20%20%CE%A4%CE%99%CE%9C-%CE%A0%CE%A9%CE%9B%CE%97%CE%A3%CE%97%CE%A3_%CE%91%CE%A5%CE%A4%CE%9F%CE%A4%CE%99%CE%9C%29%20.xml");

// 创建命名空间管理器,绑定默认命名空间到前缀"ns"
XmlNamespaceManager nsManager = new XmlNamespaceManager(xml.NameTable);
string defaultNamespace = xml.DocumentElement.NamespaceURI;
nsManager.AddNamespace("ns", defaultNamespace);

// 使用带前缀的XPath查询,同时传入命名空间管理器
XmlNodeList aNodes = xml.SelectNodes("/ns:InvoicesDoc/ns:invoice/ns:issuer/ns:vatNumber", nsManager);

foreach (XmlNode aNode in aNodes)
{
    // 注意:vatNumber是元素节点,不是属性!原代码错误地把它当成了属性
    aNode.InnerText = "123456789";
}

xml.Save(@"C:\Users\Kostas\Desktop\mydata\infinal.xml");

另外要纠正一个小错误:你原代码里把vatNumber当成了属性,但它实际上是一个独立的元素节点,直接修改InnerText就能完成内容替换。

针对微软books.xml的测试验证

微软的books.xml本身没有命名空间,只要修正了Load的调用方式,xml.SelectNodes("/catalog/book")就能正常返回节点了。你之前测试失败大概率也是因为Load的赋值错误导致的。


内容的提问来源于stack exchange,提问作者Kostas L

火山引擎 最新活动