在 PHP 中使用 XMLReader 读取子节点
Reading child nodes with XMLReader in PHP
背景:我有一个从资源 material 和 m.sarna.net 收集的恒星系统列表。该数据使用不同的 PHP 文件转换为 xml 文件,此处不予讨论。我正在从浏览器调用下面的 php 文件,传递名称和长度变量。我正在尝试使用 XMLReader 来定位特定节点以进行检索,但返回的数据太多了。我没有返回一个元素,然后继续下一个元素,而是重复获得相同的元素,如果我愿意的话,可以达到数千个。它应该很简单,但我不知道我错过了什么。请帮忙。如果您有兴趣,这是为 Battletech 准备的。虽然此文件有 7889 条跳跃路径,但包含双跳的文件,距离可达 60 光年,包含大约 24000 个条目,因此文件大小约为 4MB。每次需要时我都不想读入内存。
<jumpPathsStandard summary="Unique Jump Paths under 30 light years: 7889">
<Terra>
<from>Terra</from>
<to>Thorin</to>
<distance>24.35</distance>
<fromX>0.00</fromX>
<fromY>0.00</fromY>
<toX>-23.73</toX>
<toY>8.08</toY>
</Terra>
<Terra>
<from>Terra</from>
<to>Yorii</to>
<distance>22.47</distance>
<fromX>0.00</fromX>
<fromY>0.00</fromY>
<toX>-8.08</toX>
<toY>21.39</toY>
</Terra>
<Terra_Firma>
<from>Terra Firma</from>
<to>Woodstock</to>
<distance>22.36</distance>
<fromX>22.69</fromX>
<fromY>-33.90</fromY>
<toX>44.60</toX>
<toY>-37.03</toY>
</Terra_Firma>
<Tetersen>
<from>Tetersen</from>
<to>Tharkad</to>
<distance>12.53</distance>
<fromX>-204.99</fromX>
<fromY>146.05</fromY>
<toX>-215.94</toX>
<toY>152.83</toY>
</Tetersen>
$i=0;
if(isset($_GET["name"]) && isset($_GET["length"])) {
switch ($_GET["length"]) {
case "short":
$xml = new XMLReader();
$xml->open($shortfile);
$items = array();
while($xml->read() && $xml->name !== $_GET['name']);
while($xml->name === $_GET['name']) {
$item = array();
$node = new SimpleXMLElement($xml->readOuterXML());
if($node->from == $_GET['name']) {
echo $i.": ".$node->from." | ".$node->to." | ".$node->distance." | ".$node->fromX." | ".$node->fromY." | ".$node->toX." | ".$node->toY."<br>";
$i++;
}
}
$xml->$close();
break;
case "long":
# Future use;
break;
}
}
我得到的输出:
测试
0:泰拉 |索林 | 24.35 | 0.00 | 0.00 | -23.73 | 8.08
1:泰拉 |索林 | 24.35 | 0.00 | 0.00 | -23.73 | 8.08
2:泰拉 |索林 | 24.35 | 0.00 | 0.00 | -23.73 | 8.08
3:泰拉 |索林 | 24.35 | 0.00 | 0.00 | -23.73 | 8.08
4:泰拉 |索林 | 24.35 | 0.00 | 0.00 | -23.73 | 8.08
5:泰拉 |索林 | 24.35 | 0.00 | 0.00 | -23.73 | 8.08
...
您缺少在读取循环中移动到下一项的代码
$xml->next($_GET['name']);
所以...
while($xml->name === $_GET['name']) {
$item = array();
$node = new SimpleXMLElement($xml->readOuterXML());
if($node->from == $_GET['name']) {
echo $i.": ".$node->from." | ".$node->to." | ".$node->distance." | ".$node->fromX." | ".$node->fromY." | ".$node->toX." | ".$node->toY."<br>";
$i++;
}
// Next item...
$xml->next($_GET['name']);
}
$xml->$close();
背景:我有一个从资源 material 和 m.sarna.net 收集的恒星系统列表。该数据使用不同的 PHP 文件转换为 xml 文件,此处不予讨论。我正在从浏览器调用下面的 php 文件,传递名称和长度变量。我正在尝试使用 XMLReader 来定位特定节点以进行检索,但返回的数据太多了。我没有返回一个元素,然后继续下一个元素,而是重复获得相同的元素,如果我愿意的话,可以达到数千个。它应该很简单,但我不知道我错过了什么。请帮忙。如果您有兴趣,这是为 Battletech 准备的。虽然此文件有 7889 条跳跃路径,但包含双跳的文件,距离可达 60 光年,包含大约 24000 个条目,因此文件大小约为 4MB。每次需要时我都不想读入内存。
<jumpPathsStandard summary="Unique Jump Paths under 30 light years: 7889">
<Terra>
<from>Terra</from>
<to>Thorin</to>
<distance>24.35</distance>
<fromX>0.00</fromX>
<fromY>0.00</fromY>
<toX>-23.73</toX>
<toY>8.08</toY>
</Terra>
<Terra>
<from>Terra</from>
<to>Yorii</to>
<distance>22.47</distance>
<fromX>0.00</fromX>
<fromY>0.00</fromY>
<toX>-8.08</toX>
<toY>21.39</toY>
</Terra>
<Terra_Firma>
<from>Terra Firma</from>
<to>Woodstock</to>
<distance>22.36</distance>
<fromX>22.69</fromX>
<fromY>-33.90</fromY>
<toX>44.60</toX>
<toY>-37.03</toY>
</Terra_Firma>
<Tetersen>
<from>Tetersen</from>
<to>Tharkad</to>
<distance>12.53</distance>
<fromX>-204.99</fromX>
<fromY>146.05</fromY>
<toX>-215.94</toX>
<toY>152.83</toY>
</Tetersen>
$i=0;
if(isset($_GET["name"]) && isset($_GET["length"])) {
switch ($_GET["length"]) {
case "short":
$xml = new XMLReader();
$xml->open($shortfile);
$items = array();
while($xml->read() && $xml->name !== $_GET['name']);
while($xml->name === $_GET['name']) {
$item = array();
$node = new SimpleXMLElement($xml->readOuterXML());
if($node->from == $_GET['name']) {
echo $i.": ".$node->from." | ".$node->to." | ".$node->distance." | ".$node->fromX." | ".$node->fromY." | ".$node->toX." | ".$node->toY."<br>";
$i++;
}
}
$xml->$close();
break;
case "long":
# Future use;
break;
}
}
我得到的输出: 测试
0:泰拉 |索林 | 24.35 | 0.00 | 0.00 | -23.73 | 8.08
1:泰拉 |索林 | 24.35 | 0.00 | 0.00 | -23.73 | 8.08
2:泰拉 |索林 | 24.35 | 0.00 | 0.00 | -23.73 | 8.08
3:泰拉 |索林 | 24.35 | 0.00 | 0.00 | -23.73 | 8.08
4:泰拉 |索林 | 24.35 | 0.00 | 0.00 | -23.73 | 8.08
5:泰拉 |索林 | 24.35 | 0.00 | 0.00 | -23.73 | 8.08 ...
您缺少在读取循环中移动到下一项的代码
$xml->next($_GET['name']);
所以...
while($xml->name === $_GET['name']) {
$item = array();
$node = new SimpleXMLElement($xml->readOuterXML());
if($node->from == $_GET['name']) {
echo $i.": ".$node->from." | ".$node->to." | ".$node->distance." | ".$node->fromX." | ".$node->fromY." | ".$node->toX." | ".$node->toY."<br>";
$i++;
}
// Next item...
$xml->next($_GET['name']);
}
$xml->$close();