将XML转换为具有属性名称的数组

时间:2017-03-23 09:16:22

标签: php simplexml

关于将XML转换为数组有一些非常简单的问题,最简单的方法如下:

$data = unserialize(serialize(json_decode(json_encode((array)simplexml_load_string($dataXml)), 1)));

但是,我无法使用此方法获取属性名称,并且无法在SO上找到任何问题,并解释了如何执行此操作。

以下是我拥有的XML的一部分:

<Object>
                <attribute name="Surname">Ярош</attribute>
                <attribute name="Name">Анна</attribute>
                <attribute name="Middle name">Григорьевна</attribute>
                <attribute name="Position">Торговый представитель розничных продаж</attribute>
                <attribute name="City">BAIKALSEA Company Иркутск</attribute>
                <attribute name="Division">Отдел продаж</attribute>
                <attribute name="Department">Продажи</attribute>
                <attribute name="Email">yarosh@baikalsea.com</attribute>
                <attribute name="MobPhone">79149274726</attribute>
                <attribute name="WorkPhone">-</attribute>
                <attribute name="Manager">Нет</attribute>
                <attribute name="HonoredWorker">Нет</attribute>
                <attribute name="Login">yarosh@baikalsea.com</attribute>
                <attribute name="Character">Пользователь</attribute>
        </Object>

以下是我用encode / decode和simpleXml转换它的方法:

enter image description here

正如您所见,'name'属性及其值已丢失。我也需要那些name属性及其值。请任何帮助表示赞赏。

2 个答案:

答案 0 :(得分:0)

好的,我终于found函数,它将XML转换为对象,保留名称空间,属性,子元素等:

function xmlObjToArr($obj) { 
        $namespace = $obj->getDocNamespaces(true); 
        $namespace[NULL] = NULL; 

        $children = array(); 
        $attributes = array(); 
        $name = strtolower((string)$obj->getName()); 

        $text = trim((string)$obj); 
        if( strlen($text) <= 0 ) { 
            $text = NULL; 
        } 

        // get info for all namespaces 
        if(is_object($obj)) { 
            foreach( $namespace as $ns=>$nsUrl ) { 
                // atributes 
                $objAttributes = $obj->attributes($ns, true); 
                foreach( $objAttributes as $attributeName => $attributeValue ) { 
                    $attribName = strtolower(trim((string)$attributeName)); 
                    $attribVal = trim((string)$attributeValue); 
                    if (!empty($ns)) { 
                        $attribName = $ns . ':' . $attribName; 
                    } 
                    $attributes[$attribName] = $attribVal; 
                } 

                // children 
                $objChildren = $obj->children($ns, true); 
                foreach( $objChildren as $childName=>$child ) { 
                    $childName = strtolower((string)$childName); 
                    if( !empty($ns) ) { 
                        $childName = $ns.':'.$childName; 
                    } 
                    $children[$childName][] = xmlObjToArr($child); 
                } 
            } 
        } 

        return array( 
            'name'=>$name, 
            'text'=>$text, 
            'attributes'=>$attributes, 
            'children'=>$children 
        ); 
    } 

答案 1 :(得分:0)

我认为你从根本上说是错误的做法。不要尝试创建一个可以在一个数组中表达XML文档的所有可能内容的函数,而是使用SimpleXML提供的API 提取特定任务所需的数据

根据您的示例输入,有用的输出可能是键值对的关联数组,如下所示:

Array (
    [Surname] => Ярош
    [Name] => Анна
    [Middle name] => Григорьевна
    [Position] => Торговый представитель розничных продаж
    [City] => BAIKALSEA Company Иркутск
    [Division] => Отдел продаж
    [Department] => Продажи
    [Email] => yarosh@baikalsea.com
    [MobPhone] => 79149274726
    [WorkPhone] => -
    [Manager] => Нет
    [HonoredWorker] => Нет
    [Login] => yarosh@baikalsea.com
    [Character] => Пользователь 
)

可以通过SimpleXML元素上的简单循环实现:

$sx = simplexml_load_string($xml);

$parsed_attributes = [];
foreach ( $sx->attribute as $attribute_element ) {
    $parsed_attributes[ (string)$attribute_element['name'] ] = (string)$attribute_element;
}

print_r($parsed_attributes);

如果您不知道应用程序的这一部分将如何使用数据,请将其保存为SimpleXMLElement,并为其余代码提供该API的强大功能。如果要将其存储以便以后使用,请使用->asXML()并以XML格式存储它。