【问题标题】:XML R How to retrieve values (could this be a namespace issue?)XML R 如何检索值(这可能是命名空间问题吗?)
【发布时间】:2015-12-02 18:06:23
【问题描述】:

就在我以为我理解 XPath 的时候!我一定错过了一些非常简单的东西,但我无法在以下选择节点“citedby-count”的值:

xml <- "<?xml version='1.0' encoding='UTF-8'?>
        <search-results xmlns='http://www.w3.org/2005/Atom' xmlns:cto='http://www.elsevier.com/xml/cto/dtd' xmlns:atom='http://www.w3.org/2005/Atom' xmlns:prism='http://prismstandard.org/namespaces/basic/2.0/' xmlns:opensearch='http://a9.com/-/spec/opensearch/1.1/' xmlns:dc='http://purl.org/dc/elements/1.1/'>

            <entry>
                 <prism:url>http://api.elsevier.com/content/abstract/scopus_id/111111</prism:url>
                 <dc:title>Paper Title</dc:title>
                 <citedby-count>1</citedby-count>
            </entry> 
        </search-results>"

doc <- xmlParse(xml)

我试过了

doc["//citedby-count"]

doc["//{'citedby-count'}"]

doc["//entry"]

但都返回

list()
attr(,"class")
[1] "XMLNodeSet"

然而,

doc["//dc:title"] 

工作得很好。

我是不是看这个太久了?请帮忙!

**编辑:**我认为这是因为连字符,但不可能是因为

doc["//entry"] 

也不行。

【问题讨论】:

  • doc["//atom:citedby-count", namespaces=c(atom="http://www.w3.org/2005/Atom")](处理 R 中的默认命名空间和类似 XML 的包是一件非常痛苦的事情)
  • 啊啊啊,谢谢!我已经使用这些文档好几个星期了,从来没有遇到过命名空间的问题。是什么让 atom 成为条目和被引用计数的命名空间?我以为我有点理解他们,但现在我完全困惑了
  • 我刚刚创建了一个默认命名空间并将其命名为atom。我把它称为fredq。 XML pkg 将使用它来命名默认命名空间,然后您使用它来引用没有与它们关联的 : 命名空间的标签。
  • 好的。那个实际的命名空间在 xml 中,所以我很困惑。我发现在我的代码中我可以使用 doc["//atom:citedby-count"] 得到相同的结果,是因为 atom 已经在根节点中了吗?
  • 哦,伙计。我没有尝试过 :-) 我只是假设它在默认命名空间上很无聊(而且我没有阅读其余的内容以看到 atom 在那里)。 unlist(sapply(xmlNamespaces(doc), "[", "id")) 显示 R 读入的所有内容。我不认为 citedby-count 是实际的 Atom NS 标签。这可能是一个“走运”的例子。

标签: xml r xpath


【解决方案1】:

通用命名空间前缀被声明为xmlns:foo="...",其中foo是前缀,它在元素名称中使用显式&lt;foo:bar&gt;,其中bar是元素的本地名称.除此之外还有默认命名空间。它是没有前缀声明的命名空间,如xmlns="...",并且在声明默认前缀的元素上隐含以及后代元素,除非有东西覆盖默认命名空间继承,即具有本地默认命名空间或在后代元素的名称中使用显式前缀。

这是故事的第一部分,关于 XML 中的命名空间。另一方面,XPath 不知道默认命名空间。在 XPath 中,没有前缀的元素总是被认为是在空的命名空间中。为了弥合 XML 和 XPath 在默认命名空间方面的区别,通常当您需要查询默认命名空间中的元素时,您必须定义一个指向 XML 的默认命名空间的前缀,并在 XPath 表达式中使用该前缀。这基本上是@hrbrmstr 在第一条评论中建议的内容,如下所示(前缀可以是任何东西,只要它映射到正确的默认命名空间):

doc["//d:citedby-count", namespaces=c(d="http://www.w3.org/2005/Atom")]

但事实证明,您的 XML 有一个显式前缀 atom,它已经指向同一个命名空间 uri,可以直接使用。

【讨论】:

  • 谢谢,这帮助我更多地理解了命名空间。但是here 是一个我在没有明确引用命名空间的情况下广泛导航的文件(除非元素这样做)而且我从来没有遇到过问题。你觉得有什么不同?
  • @SarahHailey 当然,该链接中的 XML 没有任何默认命名空间。那里的所有命名空间都用前缀声明(xmlns:some_prefix_here="..." 与默认命名空间模式 xmlns="..." 对比)
  • 谢谢!超级好用。
【解决方案2】:

您也可以使用doc["//x:citedby-count", namespace = "x"] 来处理默认命名空间(来自xpathApply 的示例)。

【讨论】:

    猜你喜欢
    • 2013-07-20
    • 1970-01-01
    • 2015-02-21
    • 2020-03-04
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多