PHP 和 XML。使用 PHP 循环遍历 XML 文件
Posted
技术标签:
【中文标题】PHP 和 XML。使用 PHP 循环遍历 XML 文件【英文标题】:PHP and XML. Looping through an XML file with PHP 【发布时间】:2011-10-13 19:52:31 【问题描述】:我现在正沉浸在 foreach 炼狱中,试图想出一种方法来用 php 遍历这个 XML 文件(下面的实际 XML 文本)(遵循 XML 文件内容。) 我想做的是以下几点:
-
获取所有文件夹元素名称
如果文件夹元素具有“是”作为子文件夹属性,则向下移动一个级别并获取该文件夹元素的名称
如果不移动到下一个文件夹元素
画廊列表.xml:
<?xml version="1.0" encoding="ISO-8859-1"?>
<gallerylisting exists="yes">
<folder subfolder="yes">
Events
<folder subfolder="yes">
Beach_Clean_2010
<folder subfolder="no">
Onna_Village
</folder>
<folder subfolder="no">
Sunabe_Sea_Wall
</folder>
</folder>
</folder>
<folder subfolder="no">
Food_And_Drink
</folder>
<folder subfolder="no">
Inside
</folder>
<folder subfolder="no">
Location
</folder>
<folder subfolder="no">
NightLife
</folder>
</gallerylisting>
gallerylisting.php
<?php
$xmlref = simplexml_load_file("gallerylisting.xml");
foreach($xmlref->children() as $child)
foreach($child->attributes() as $attr => $attrVal)
print $child;
if($attrVal == "yes")
foreach($child->children() as $child)
echo $child;
foreach($child->attributes() as $attr => $attrVal)
if($attrVal == "yes")
foreach($child->children() as $child)
echo $child;
我正在......计数...... 5 个 foreach 循环深入到这个 PHP 脚本中,我一点也不喜欢它,而且如果我的文件夹有另一个子文件夹,我将不得不添加它
$if(attrVal=="yes")...etc.
再次进入,好吧......不!无论如何我可以避免这种情况。我是 PHP 新手,尤其是 PHP 和 XML。
感谢您的帮助。
【问题讨论】:
当你用效率标记这个问题时,我会提出这一点。您的 xml 中不需要“子文件夹”属性。 PHP-Library 将帮助您了解该节点是否有子节点。如果有,请递归使用@Matt 的函数。您不应该将“文本”元素(例如您的文件夹名称)与节点混合。这看起来有点恶心。尝试使用“名称”属性。 注意以备将来参考!谢谢你的坦率! (badump ch!) 【参考方案1】:您可以尝试使用xpath 代替嵌套循环方法..
运行查询
gallerylisting//folder[@subfolder="yes"]/text()
在上面给出的 xml 文档中,使用 this xpath tester 会给出结果事件和 Beach_Clean_2010,这就是我认为你想要的。该查询将查找根节点gallerylisting 下的所有文件夹元素,如果它们具有等于“yes”的子文件夹属性,则将返回该节点中的文本。
所以,在 PHP 中,我们有
<?php
$xmldoc = new DOMDocument();
$xmldoc->load('gallerylisting.xml');
$xpathvar = new Domxpath($xmldoc);
$queryResult = $xpathvar->query('gallerylisting//folder[@subfolder="yes"]/text()');
foreach($queryResult as $result)
echo $result->textContent;
?>
我不是 PHP 人,所以我相信 this *** question 中的代码可以正常工作。需要注意的一件事是,在 xpath 中使用 //name 意味着查找从当前位置下降并与该名称匹配的所有节点。这在大型文档上可能非常慢。
似乎有多种方法可以用 PHP 处理 xpath。来自this page 的示例执行如下查询:
$result = $xml->xpath("gallerylisting//folder[@subfolder="yes"]/text()");
print_r($result);
?>
【讨论】:
【参考方案2】:递归在这里可能对你有益。
<?php
function display_entities( $xml )
foreach($xml->children() as $child)
foreach($child->attributes() as $attr => $attrVal)
print $child;
if($attrVal == "yes")
display_entities( $child->children() );
$xmlref = simplexml_load_file("gallerylisting.xml");
display_entities($xmlref->children());
【讨论】:
我将不得不尝试你的交易,这个 xpath Wrikken 在下面谈论。到时我会给出我的答案。这似乎是我会在 javascript 中做的事情,所以是的,它还很遥远。 是的!是的!这就是它兄弟,这完全是它。我在实际调用它时在 display_entities 参数中做了一些小改动,我只使用了 $xmlref。这让我得到了一切!你是邪恶的兄弟。 您应该使用一个标志并将 if 移出内部 foreach 循环,否则内部 display_entitties 可能会被多次调用,而只有真的需要每个孩子一次。【参考方案3】:使用 XPath:
如果 subfolder=no 在叶子中不可靠(即“否”可能并不总是设置):
foreach($xmlref->xpath('//folder[not(@subfolder) or @subfolder!="yes"]') as $node)
如果是:
foreach($xmlref->xpath('//folder[@subfolder="no"]') as $node)
或者即使您想检查没有文件夹子文件夹的文件夹,也可以忽略属性:
foreach($xmlref->xpath('//folder[not(folder)]') as $node)
【讨论】:
我将不得不研究 xpath 的考验。它看起来很合法。以上是关于PHP 和 XML。使用 PHP 循环遍历 XML 文件的主要内容,如果未能解决你的问题,请参考以下文章
如何循环访问和访问多维和关联数组中的各种元素? PHP,JSON 或 XML