2012-02-08 76 views
1

我正在使用亞馬遜產品廣告API的接口。xpath從嵌套元素中獲取數據

我有XML,其中包括類似如下的內容:

<BrowseNodes> 
    <BrowseNode> 
    <Name>Category</Name> 
    <BrowseNodeId>123456</BrowseNodeId> 
    <Ancestors> 
     <BrowseNode> 
     <Name>Whatever</Name> 
     <BrowseNodeId>987654</BrowseNodeId> 
     <BrosweNode> 
    </Ancestors> 
    </BroseNode> 
    <BroseNode> 
    ... 
    </BrowseNode> 
</BrowseNodes> 

我得仔細檢查我的XML。除了我上面發佈的第一個<BrowseNode>以外,可能還有一個級別爲<BrowseNode></BrowseNode>

我需要找到<BrowseNode><Name>那是祖先元素中,其中<Ancestors>元素是<Name>類別</Name>

我剛開始使用的XPath的兄弟,這是在我的頭上。

我一直在編碼這樣的:

//$XML fromapi 
$parsed=simplexml_load_string($XML); 

//narrow it down 
$s = '/ItemSearchResponse/Items/Item'; 
$items = $parsed->xpath($s); 

//Get only the top level BrowseNodes for this item. 
foreach($items as $item) 
    { 
    // this narrows it down close to what I posted above. 
    $s = 'BrowseNodes/BrowseNode'; 
    $top_browsenode_search=$item->xpath($s); 

     //there may be a simpler way, but I think it is working for me: 
     foreach ($top_browsenode_search as $top_browsenode) 
     { 
      $temp_array=array();//must be emptied each time. 
      $s = 'Name'; 
      $temp_array['name']=$top_browsenode->xpath($s); 
      $s = 'BrowseNodeId'; 
      $temp_array['id']=$top_browsenode->xpath($s); 

     $browsenodes[]=$temp_array; 
     } 
    $top_browsenodes[]=$browsenodes; 
    unset ($browsenodes);   
    }  

有沒有人能夠幫助與XPath語法?如果不是直接的話,你能否指點我所知道的任何新手友好的文檔?我就這個主題下載了一本很棒的書,我從中學到了很多東西,但是它有點凌駕於我的頭上。

以下不是問題的一部分,而是證明其中一個答案是正確的。詳情請參閱評論。 預期的結果: 「隨便」 給定結果: 「無論」

<?xml version="1.0" ?> 
<root> 
<BrowseNodes> 
    <BrowseNode> 
    <Name>Category</Name> 
    <BrowseNodeId>123456</BrowseNodeId> 
    <Ancestors> 
     <BrowseNode> 
     <Name>Whatever</Name> 
     <BrowseNodeId>987654</BrowseNodeId> 
     </BrowseNode> 
    </Ancestors> 
    </BrowseNode> 
    <BrowseNode> 
    <Name>SomethingElse</Name> 
    <BrowseNodeId>951753</BrowseNodeId> 
    </BrowseNode> 
</BrowseNodes> 
</root> 
BrowseNodes/BrowseNode/Name 
Array 
(
    [0] => SimpleXMLElement Object 
     (
      [0] => Category 
     ) 

    [1] => SimpleXMLElement Object 
     (
      [0] => SomethingElse 
     ) 

) 

BrowseNodes/BrowseNode[Name="Category"]/Ancestors/BrowseNode/Name 
Array 
(
    [0] => SimpleXMLElement Object 
     (
      [0] => Whatever 
     ) 

) 

謝謝!

回答

1

如果你想要得到的只是節點:

BrowserNodes/BrowserNode[Name=_______]/Ancestors/BrowserNode/Name 

如果你想獲得該節點的文本:

BrowserNodes/BrowserNode[Name=_______]/Ancestors/BrowserNode/Name/text() 

在這兩個例子中,使用的名稱替換_你正在搜索。

+0

謝謝,它看起來像我需要你的第二個,我會做$ S =「BrowseNodes/BrowseNode [名稱=類別] /祖先/ BrowserNode /名稱/文本( )'但是這是否遍歷了深度,還是我需要知道它的嵌套深度? – TecBrat 2012-02-08 04:20:18

+0

如果你不確定'BrowserNodes'(帶有「s」)是多麼深的嵌套,在整個事物的前面添加'descendant ::'。順便說一下,我對XPath的這個級別知之甚少。我只是使用[this](http://www.w3schools.com/xpath/xpath_axes.asp)。 – Zenexer 2012-02-08 04:26:33

+0

我發現(至少對我而言)總是有學習曲線,即使在理解新技術的文檔時也是如此。我仍在研究這個問題,所以我很欣賞你能夠將這些信息分解到我目前的水平。我將採取這種做法,不僅要獲得這一塊數據,還要進一步理解xpath查詢。謝謝! – TecBrat 2012-02-08 13:39:36

-1

查找下面的例子:

<?php 
$xmlString =" 
<BrowseNodes> 
    <BrowseNode> 
    <Name>Category</Name> 
    <BrowseNodeId>123456</BrowseNodeId> 
    <Ancestors> 
     <BrowseNode> 
     <Name>Whatever</Name> 
     <BrowseNodeId>987654</BrowseNodeId> 
     </BrowseNode> 
    </Ancestors> 
    </BrowseNode> 
<BrowseNode> 
    <Name>Category</Name> 
    <BrowseNodeId>123456</BrowseNodeId> 
    <Ancestors> 
     <BrowseNode> 
     <Name>Whatever</Name> 
     <BrowseNodeId>987654</BrowseNodeId> 
     </BrowseNode> 
    </Ancestors> 
    </BrowseNode> 
</BrowseNodes>"; 
$result= simplexml_load_string($xmlString); 
$counter =0; 
$newArray=array(); 
foreach($result->BrowseNode as $arr) { 
    $newArray[$counter]['Name'] =(string)$arr->Name; 
    $newArray[$counter]['BrowseNodeId'] =(string)$arr->BrowseNodeId; 
    $newArray[$counter]['Ancestors']['Name'] =(string)$arr->Ancestors->BrowseNode->Name; 
    $newArray[$counter]['Ancestors']['BrowseNodeId'] =(string)$arr->Ancestors->BrowseNode->BrowseNodeId;  
    $counter++; 
} 
print"<pre>"; 
print_r($newArray); 
die; 
?> 
+0

這並不是真正的原始海報所要求的。我相信TecBrat已經能夠使用這種技術。現在他想用XPath簡化它。 – Zenexer 2012-02-09 04:04:09

+0

我實際上重新提出了我的問題並再次發佈。我被給了這段代碼,它工作:'BrowseNodes/BrowseNode // BrowseNode [Name =「Categories」]'看起來我真正需要的是雙斜線。我現在已經可以用這些新知識做一些類似的搜索。 **他** :) – TecBrat 2012-02-09 04:39:31

+0

噢,我遺漏了部分工作代碼:'BrowseNodes/BrowseNode // BrowseNode [Name =「Categories」]/Ancestors/BrowseNode/Name/text()' – TecBrat 2012-02-09 04:52:24