2014-09-05 49 views
0

我只是試圖通過迭代遍歷PHP中的XML文件的所有節點名稱。這是我的嘗試:使用PHP迭代DOM文檔

$doc = new DOMDocument(); 
$doc->preserveWhiteSpace = false; 
$doc->loadXML("<?xml version='1.0' encoding='ISO-8859-1'?><user><name>Michael Taylor</name><offers>0</offers><address><street>Ringstreet 8</street><zip>1100</zip><city>Norther</city></address><credit>473.43</credit></user>"); 
$node = $doc->firstChild; 

function iterateXML($node) { 
    if($node->childNodes->length == 0) { 
     echo $node->nodeName; 
     return; 
    } 
    $children = $node->childNodes; 
    foreach($children as $child) { 
     iterateXML($child); 
    } 
} 
iterateXML($node); 

然而,輸出

#text#text#text#text#text#text 

我在做什麼錯?

編輯:

我最後的計劃是給孩子添加名字被分隔的父節點的名稱,「_」,所以對於例如最終輸出上面應該是:

name 
offers 
address_street 
address_zip 
address_city 
credit 

最簡單的方法是什麼?

回答

2

不僅元素是節點。您輸出沒有孩子的節點的名稱。在只有文本節點的XML中。

你可以檢查節點類型...或使用XPath:

$xml = <<<'XML' 
<?xml version='1.0' encoding='ISO-8859-1'?><user><name>Michael Taylor</name><offers>0</offers><address><street>Ringstreet 8</street><zip>1100</zip><city>Norther</city></address><credit>473.43</credit></user> 
XML; 

$dom = new DOMDocument(); 
$dom->loadXml($xml); 
$xpath = new DOMXPath($dom); 

foreach ($xpath->evaluate('//*[count(*) = 0]') as $node) { 
    var_dump($node->nodeName); 
} 

*匹配的元素節點,//*意味着文檔中的任何元素節點,[count(*) = 0]它限制節點無子元素節點。

輸出:

string(4) "name" 
string(6) "offers" 
string(6) "street" 
string(3) "zip" 
string(4) "city" 
string(6) "credit" 
+0

大,但是它也可以使用XPath的子節點的名稱添加到父節點的名稱? (見編輯的OP) – user3255675 2014-09-06 10:07:12

+1

這裏有幾種方法來解決這個問題。節點具有parentNode屬性。以下是可以使用的XPath中的「祖先」和「父」軸。但是如果你考慮一下'name'有一個父節點'user'。將XML轉換爲數組的大部分時間都是錯誤的方式。通過直接通過Xpath讀取XML,您仍然可以使用您仍然可以使用的信息。 – ThW 2014-09-06 15:41:55