Как я могу использовать запросы xpath с использованием библиотеки XML R? - PullRequest
8 голосов
/ 07 октября 2010

XML-файл имеет этот фрагмент:

<?xml version="1.0"?>
<PC-AssayContainer
    xmlns="http://www.ncbi.nlm.nih.gov"
    xmlns:xs="http://www.w3.org/2001/XMLSchema-instance"
    xs:schemaLocation="http://www.ncbi.nlm.nih.gov ftp://ftp.ncbi.nlm.nih.gov/pubchem/specifications/pubchem.xsd"
>
....
    <PC-AnnotatedXRef>
      <PC-AnnotatedXRef_xref>
        <PC-XRefData>
          <PC-XRefData_pmid>17959251</PC-XRefData_pmid>
        </PC-XRefData>
      </PC-AnnotatedXRef_xref>
    </PC-AnnotatedXRef>

Я попытался разобрать его с помощью глобального поиска xpath, а также попытался с некоторым пространством имен:

library('XML')
doc = xmlInternalTreeParse('http://s3.amazonaws.com/tommy_chheng/pubmed/485270.descr.xml')
>xpathApply(doc, "//PC-XRefData_pmid")
list()
attr(,"class")
[1] "XMLNodeSet"
> getNodeSet(doc, "//PC-XRefData_pmid")
list()
attr(,"class")
[1] "XMLNodeSet"
> xpathApply(doc, "//xs:PC-XRefData_pmid", ns="xs")
list()
> xpathApply(doc, "//xs:PC-XRefData_pmid", ns= c(xs = "http://www.w3.org/2001/XMLSchema-instance"))
list()

Не должен совпадать xpath:

<PC-XRefData_pmid>17959251</PC-XRefData_pmid>

Ответы [ 2 ]

9 голосов
/ 07 октября 2010

Поскольку пространство имен по умолчанию - это пространство NIH (чей URI равен "http://www.ncbi.nlm.nih.gov"), <PC-XRefData_pmid> (и все остальные элементы в вашем XML-документе, которые не имеют префикса пространства имен) находятся в этом пространстве имен NIH.

Итакчтобы сопоставить их с XPath, вам нужно сообщить процессору XPath, какой префикс вы собираетесь использовать для пространства имен NIH, и вам нужно использовать этот префикс в вашем XPath.

Итак, не зная R,Я бы попробовал

xpathApply(doc, "//nih:PC-XRefData_pmid",
   ns= c(nih = "http://www.ncbi.nlm.nih.gov"))

или

getNodeSet(doc, "//*[local-name() = 'PC-XRefData_pmid']")

, так как последний обходит пространства имен.

Просто потому, что документ XML объявляет пространство имен NIH как пространство по умолчанию, которое не 'Это означает, что процессор XPath будет знать это. В информационной модели XML префиксы пространства имен не имеют значения. Поэтому, когда я анализирую документ XML, не должно иметь значения, связано ли пространство имен NIH сПрефикс «nih:» или префикс «snizzlefritz:» или префикс «» (по умолчанию). Считается, что анализатору XML или процессору XPath не нужно знать, какой префикс привязан к какому пространству именв документе XML.Тем более что может быть несколько разных префиксов, привязанных к одному и тому же пространству имен в разных местах одного и того же документа ... и наоборот.Поэтому, если вы хотите, чтобы ваше выражение XPath совпадало с элементом, который находится в пространстве имен, вы должны объявить это пространство имен процессору XPath.

Редактировать: Есть несколько предостережений, внесенных@Jim Pivarski:

  • "Документ" должен быть узлом xml, а не документом (класс "XMLNode" или "XMLInternalElementNode", а не "XMLDocument" или "XMLInternalDocument").
  • По крайней мере, в версии Джима (XML_3.93-0) именованный аргумент - это «пространства имен», а не «ns».

Так что, если «doc» является экземпляром класса документа,правильное решение:

xpathApply(xmlRoot(doc), "//nih:PC-XRefData_pmid",
   namespaces = c(nih = "http://www.ncbi.nlm.nih.gov"))
1 голос
/ 07 октября 2010

Это FAQ.

Это: //PC-XRefData_pmid

Означает: любой PC-XRefData_pmid в документе без пространства имен или пустого пространства имен

Это не означает, что PC-XRefData_pmid в документе в пространстве имен по умолчанию

Кроме того, образец документа не завершен, но, похоже, ваш элемент PC-XRefData_pmid находится под http://www.ncbi.nlm.nih.gov пространством имен

...