我编写了一个函数,它删除标题与我的标题数组过滤器中的一个标题不匹配的所有<product>...</product>
个节点。
我的问题是,4个XML文件被保存并修改正确并保存但一个XML文件被完全破坏......
在我在这张XML表上调用该函数之后,我只看到:
<?xml version="1.0" encoding="utf-8"?>
<products/>
修改前:
<?xml version="1.0" encoding="utf-8"?>
<products>
<product>
<title>METRO</title>
<price>10.99</price>
<platform>Steam</platform>
</product>
<product>
<title>XBOX Live Gold</title>
<price>46.99</price>
<platform>Xbox</platform>
</product>
</products>
这是我的功能:
function filterGames($dom){
$xpathQuery = "/products/product";
$xp = new DomXpath($dom);
$items = $xp->query($xpathQuery);
echo "(filterGames) Delete Games\n";
foreach ($items as $item) {
$title = $item->getElementsByTagName('title')->item(0)->textContent;
if (!(array_search(mb_strtolower($title), array_map('mb_strtolower', $GLOBALS["titleArray"])))) {
//if (!(in_array($title, $GLOBALS["titleArray"]))) {
$item->parentNode->removeChild($item);
echo "Removed: " . $title ."\n";
}
}
}
有没有人知道为什么要保存和修改4个XML文件,但是一个文件完全被破坏了?
我也转换了过滤器修改XML文件的顺序,但它没有做出改变。同样,其他4个文件得到保存和修改,但一个被销毁。并且它总是被销毁的XML文件相同!
我也输入if条件,因为我看到了echo
。但无论如何......文件被破坏了。
编辑:
以下是我在filterGames
修改之前和之后的XML表的另外两个示例。它们看起来与被filterGames
修改前的XML文件1:
<?xml version="1.0" encoding="UTF-8"?>
<products>
<product>
<price>11.69</price>
<price_base>12.99</price_base>
<title>Final Fantasy VII</title>
</product>
<products>
修改后的XML文件1看起来与bevor一样,只是因为某些节点与$GLOBALS["titleArray"]
过滤器不匹配而被删除了。
修改前的XML文件2:
<products>
<product>
<title>Battlefield 2</title>
<price>5.95</price>
</product>
<products>
修改后的XML文件2看起来与bevor一样,只是因为某些节点与$GLOBALS["titleArray"]
过滤器不匹配而被删除了。
我发现了一个有趣的事实!
我的XML文件在被filterGames()
过滤后被销毁,同时也不是唯一被破坏的XML文件。这两个文件都由我的csvToXML(...)
函数从CSV转换为XML。所以我认为原因一定是这个! - 因为所有其他XML文件都无法转换!
function csvToXML($inputFilename, $outputFilename, $delimiter = ',')
{
// Open csv to read
$inputFile = fopen($inputFilename, 'rt');
// Get the headers of the file
$headers = fgetcsv($inputFile, 0, $delimiter);
// Create a new dom document with pretty formatting
$doc = new DOMDocument('1.0', 'utf-8');
$doc->preserveWhiteSpace = false;
$doc->formatOutput = true;
// Add a root node to the document
$root = $doc->createElement('products');
$root = $doc->appendChild($root);
// Loop through each row creating a <row> node with the correct data
while (($row = fgetcsv($inputFile, 0, $delimiter)) !== false) {
$container = $doc->createElement('product');
foreach ($headers as $i => $header) {
$child = $doc->createElement($header);
$child = $container->appendChild($child);
$value = $doc->createTextNode($row[$i]);
$value = $child->appendChild($value);
}
$root->appendChild($container);
}
$strxml = $doc->saveXML();
$handle = fopen($outputFilename, 'w');
fwrite($handle, $strxml);
fclose($handle);
}
答案 0 :(得分:1)
这是一个如何运作的例子:
<?php
function filterGames($dom) {
$xpathQuery = "/products/product";
$xp = new DOMXpath($dom);
$items = $xp->query($xpathQuery);
// convert the array since this can be one time
$titles = array_map('mb_strtolower', $GLOBALS['titleArray']);
// loop over the products in the xml
foreach ($items as $item) {
// convert the title to lowercase
$title = mb_strtolower($item->getElementsByTagName('title')->item(0)->textContent);
// check if the title is not in the array of titles
// if not in the arr, then remove it
if(!in_array($title, $titles)) {
$item->parentNode->removeChild($item);
echo "Removed: " . $title ."\n";
// there needs to be a save call here
}
}
}
// array of titles
$GLOBALS['titleArray'] = array("METRO");
// load the xml document
$dom = new DOMDocument();
$dom->load("input.xml");
// call the function
filterGames($dom);
问题是array_search()
返回键而不是布尔值。因此,如果键是> = 1,那么它将被转换为true,而其他任何内容都将为false。因此可能存在误报导致产品被移除。