我已经有点干到why年了——至少在future 几年是这样.Net框架——在执行XPath查询时,有必要使用XmlNamespaceManager
来处理名称空间(或相当笨拙和冗长的[local-name()=...
XPath谓词/函数/任何东西).我理解为什么名称空间是必要的,或者至少是有益的,但它这么复杂吗?
为了查询简单的XML文档(没有名称空间).
<?xml version="1.0" encoding="ISO-8859-1"?>
<rootNode>
<nodeName>Some Text Here</nodeName>
</rootNode>
.可以使用类似于doc.SelectSingleNode("//nodeName")
的值(这将与<nodeName>Some Text Here</nodeName>
匹配)
Mystery #1:My first annoyance——如果我理解正确的话——这仅仅是向父/根标记(无论是否用作子 node 标记的一部分)添加名称空间引用,如下所示:
<?xml version="1.0" encoding="ISO-8859-1"?>
<rootNode xmlns="http://example.com/xmlns/foo">
<nodeName>Some Text Here</nodeName>
</rootNode>
...需要多行代码才能获得相同的结果:
Dim nsmgr As New XmlNamespaceManager(doc.NameTable)
nsmgr.AddNamespace("ab", "http://example.com/xmlns/foo")
Dim desiredNode As XmlNode = doc.SelectSingleNode("//ab:nodeName", nsmgr)
...本质上是虚构一个不存在的前缀("ab
")来找到一个甚至不使用前缀的 node .How does this make sense? doc.SelectSingleNode("//nodeName")
在概念上有什么问题?
Mystery #2:假设您有一个使用前缀的XML文档:
<?xml version="1.0" encoding="ISO-8859-1"?>
<rootNode xmlns:cde="http://example.com/xmlns/foo" xmlns:feg="http://example.com/xmlns/bar">
<cde:nodeName>Some Text Here</cde:nodeName>
<feg:nodeName>Some Other Value</feg:nodeName>
<feg:otherName>Yet Another Value</feg:otherName>
</rootNode>
...如果我理解正确的话,您必须将两个名称空间都添加到XmlNamespaceManager
,才能查询单个 node ……
Dim nsmgr As New XmlNamespaceManager(doc.NameTable)
nsmgr.AddNamespace("cde", "http://example.com/xmlns/foo")
nsmgr.AddNamespace("feg", "http://example.com/xmlns/bar")
Dim desiredNode As XmlNode = doc.SelectSingleNode("//feg:nodeName", nsmgr)
...在这种情况下,为什么(在概念上)我需要一个名称空间管理器?
******编辑成下面的 comments ****
Edit Added:个 我修改和改进的问题基于XmlNamespaceManager在我认为大多数情况下的明显冗余,以及使用命名空间管理器指定前缀到URI的映射:
当名称空间前缀("cde")到名称空间URI("http://example.com/xmlns/foo")的直接映射在源文档中明确说明时:
...<rootNode xmlns:cde="http://example.com/xmlns/foo"...
程序员在进行查询之前重新创建该映射的概念性需求是什么?