0

我有一个非常大的文件需要在 php 中解析,所以我使用的是 xmlReader。我刚刚开始使用 xml 并且遇到了一些问题....

这是xml的结构...

<?xml version="1.0" encoding="utf-8"?>
    <devices>
        <os name="os1">
            <device user_agent="uaValue1">
                <device_name>name1</device_name>
                <device_os>osValue1</device_os>
            </device>
            <device user_agent="uaValue2">
                <device_name>name2</device_name>
                <device_os>osValue2</device_os>
            </device>   
        </os>
        <os name="os2">
            <device user_agent="uaValue3">
                <device_name>name3</device_name>
                <device_os>osValue5</device_os>
            </device>
            <device user_agent="uaValue4">
                <device_name>name4</device_name>
                <device_os>osValue4</device_os>
            </device>   
        </os>
        <manufacturer name="mf1">
            <device user_agent="uaValue5">
                <device_name>name5</device_name>
                <device_os>osValue5</device_os>
            </device>
            <device user_agent="uaValue6">
                <device_name>name6</device_name>
                <device_os>osValue6</device_os>
            </device>       
        </manufacturer>
        <manufacturer name="mf2">
            <device user_agent="uaValue7">
                <device_name>name7</device_name>
                <device_os>osValue7</device_os>
            </device>
            <device user_agent="uaValue8">
                <device_name>name8</device_name>
                <device_os>osValue8</device_os>
            </device>       
        </manufacturer> 
    </devices>

我正在尝试使用以下函数来读取 xml(其中 $findby 将传递 os 或制造商 / $atr_value 是 $findby 值的属性名称 / $ua_str 是用户代理)。

function get_data($findby,$atr_value,$ua_str) {
    $data['device_name'] = '';
    $data['device_os'] = '';

    $xml = new XMLReader;
    $xml->open('devices.xml');

    while($xml->read()) {
        if ($xml->name == $findby) {
            if ($xml->getAttribute('name') == $atr_value) {
                while($xml->read()) {
                    if ($xml->name == "device") {
                        if ($xml->getAttribute('user_agent') == $ua_str) {
                            while($xml->read()) {                               
                                if ($xml->name == "device_name") {
                                    $data['device_name'] = $xml->value;
                                }
                                if ($xml->name == "device_os") {
                                    $data['device_os'] = $xml->value;
                                }
                            }
                        }
                    }                   
                }
            }
        }
    }
    $xml->close();
    return $data;
}

通过在这里和那里回显一些值,它似乎将数据拉到用户代理,但不会得到 device_name 或 device_os。

显然,这是行不通的。我在想 xml 不能以这种方式构建,这可能是问题并且很容易解决。然而,在我以前的一个版本中,它提取了数据,但它来自错误的用户代理。所以我认为这是我尝试使用 xmlReader 提取数据的方式。

有人对为什么这不起作用有任何想法吗?谢谢...

4

2 回答 2

0

您没有在外部 while 循环中检查标签类型。XMLReader 向您发送开始标签、结束标签、标签内容,您至少需要处理其中一些事件。

在您的外部循环中,检查$reader->nodeType == XMLReader::ELEMENT开头、XMLReader::END_ELEMENT结尾和XMLReader::TEXT标记内容。还有很多其他的 - 请参阅此类的 PHP 文档(值 0-17)。

于 2012-04-30T18:00:43.643 回答
0

我最终只是添加了我想要的元素作为属性并像这样调用它来获取数据......

function get_data($ua_str) {
    $data = array();

    $xml = new XMLReader;
    $xml->open('devices.xml');

    while($xml->read()) {
        if ($xml->nodeType == XMLReader::ELEMENT && $xml->name == 'device') {
            while($xml->read()) {
                if ($xml->getAttribute('user_agent') == $ua_str) {
                    $data['device_mf'] = $xml->getAttribute('device_mf');
                    $data['device_os'] = $xml->getAttribute('device_os');
                    $data['device_name'] = $xml->getAttribute('device_name');
                }
            }
        }
    }
    $xml->close();
    return $data;
}
于 2012-05-01T02:37:22.863 回答