如何将数组转换为PHP中的SimpleXML对象?


当前回答

一个简短的例子:

<?php

$test_array = array (
  'bla' => 'blub',
  'foo' => 'bar',
  'another_array' => array (
    'stack' => 'overflow',
  ),
);
$xml = new SimpleXMLElement('<root/>');
array_walk_recursive($test_array, array ($xml, 'addChild'));
print $xml->asXML();

结果

<?xml version="1.0"?>
<root>
  <blub>bla</blub>
  <bar>foo</bar>
  <overflow>stack</overflow>
</root>

键和值会被交换——你可以在array_walk之前用array_flip()来修复这个问题。array_walk_recursive需要PHP 5。你可以用array_walk代替,但你不会得到'stack' => 'overflow'在XML中。

其他回答

function toXML($data, $obj = false, $dom) {
    $is_first_level = false;
    if($obj === false) {
        $dom = new DomDocument('1.0');
        $obj = $dom;
        $is_first_level = true;
    }

    if(is_array($data)) {
        foreach($data as $key => $item) {
            $this->toXML($item, $obj->appendChild($dom->createElement($key)), $dom);
        }
    }else {
        $obj->appendChild($dom->createTextNode($data));
    }

    if($is_first_level) {
        $obj->formatOutput = true;
        return $obj->saveXML();
    }
    return $obj;
}

您可以使用我一直在研究的XMLParser。

$xml = XMLParser::encode(array(
    'bla' => 'blub',
    'foo' => 'bar',
    'another_array' => array (
        'stack' => 'overflow',
    )
));
// @$xml instanceof SimpleXMLElement
echo $xml->asXML();

会导致:

<?xml version="1.0"?>
<root>
    <bla>blub</bla>
    <foo>bar</foo>
    <another_array>
        <stack>overflow</stack>
    </another_array>
</root>

如果冗长的xml不成问题,可以使用xmlrpc_encode从数组创建xml。 www.php.net/xmlrpc_encode

注意,如果使用关联键和/或数字键,创建的XML会有所不同

<?php
// /params/param/value/struct/member
// there is a tag "member" for each element
// "member" contains a tag "name". its value is the associative key
$xml1 = xmlrpc_encode(array('a'=>'b','c'=>'d'));
$simplexml1 = simplexml_load_string($xml1);
print_r($xml1);
print_r($simplexml1);

// /params/param/value/array/data
// there is a tag "data" for each element
// "data" doesn't contain the tag "name"
$xml2 = xmlrpc_encode(array('a','b'));
$simplexml2 = simplexml_load_string($xml2);
print_r($xml2);
print_r($simplexml2);
?>

总之……我使用了onokazu的代码(谢谢!),并添加了在XML中重复标记的能力,它还支持属性,希望有人发现它有用!

 <?php

function array_to_xml(array $arr, SimpleXMLElement $xml) {
        foreach ($arr as $k => $v) {

            $attrArr = array();
            $kArray = explode(' ',$k);
            $tag = array_shift($kArray);

            if (count($kArray) > 0) {
                foreach($kArray as $attrValue) {
                    $attrArr[] = explode('=',$attrValue);                   
                }
            }

            if (is_array($v)) {
                if (is_numeric($k)) {
                    array_to_xml($v, $xml);
                } else {
                    $child = $xml->addChild($tag);
                    if (isset($attrArr)) {
                        foreach($attrArr as $attrArrV) {
                            $child->addAttribute($attrArrV[0],$attrArrV[1]);
                        }
                    }                   
                    array_to_xml($v, $child);
                }
            } else {
                $child = $xml->addChild($tag, $v);
                if (isset($attrArr)) {
                    foreach($attrArr as $attrArrV) {
                        $child->addAttribute($attrArrV[0],$attrArrV[1]);
                    }
                }
            }               
        }

        return $xml;
    }

        $test_array = array (
          'bla' => 'blub',
          'foo' => 'bar',
          'another_array' => array (
            array('stack' => 'overflow'),
            array('stack' => 'overflow'),
            array('stack' => 'overflow'),
          ),
          'foo attribute1=value1 attribute2=value2' => 'bar',
        );  

        $xml = array_to_xml($test_array, new SimpleXMLElement('<root/>'))->asXML();

        echo "$xml\n";
        $dom = new DOMDocument;
        $dom->preserveWhiteSpace = FALSE;
        $dom->loadXML($xml);
        $dom->formatOutput = TRUE;
        echo $dom->saveXml();
    ?>

使用FluidXML,您可以从一个PHP数组开始,生成一个用于SimpleXML的XML…只有两行代码。

$fluidxml  = fluidxml($array);
$simplexml = simplexml_import_dom($fluidxml->dom());

一个示例数组可以是

$array = [ 'doc' => [
              'fruit' => 'orange',
              'cake'  => [
                   '@id' => '123', 
                   '@'   => 'tiramisu' ],
              [ 'pasta' => 'matriciana' ],
              [ 'pasta' => 'boscaiola'  ]
] ];

https://github.com/servo-php/fluidxml