2012-07-11 13 views
19

SimpleXMLアトリビュートを配列にエスケープする方法はありますか?SimpleXMLアトリビュートへの配列

$result = $xml->xpath($xpath); 
$element = $result[ 0 ]; 
$attributes = (array) $element->attributes(); 
$attributes = $attributes[ '@attributes' ]; 

キー/値のペアを抽出するだけでループする必要はありません。私が必要とするのは、それを配列に入れて渡すことだけです。私はattributes()がデフォルトでそれをやっただろうと思っていたでしょう。しかし、私は上記の解決策をどこからでも見つけることができず、私はそれを私自身で理解しなければなりませんでした。これを複雑にすることは何ですか?

編集:私は@attributesアレイにアクセスすることは安全であるかどうかを確実に知るまで、私はまだ上記のスクリプトを使用してい

答えて

11

'@attributes'プロパティを直接読み取らないでください。これは内部使用のためです。とにかく、attributes()は、実際の配列に「変換」する必要なしに、すでに配列として使用することができます。例えば

<?php 
$xml = '<xml><test><a a="b" r="x" q="v" /></test><b/></xml>'; 
$x = new SimpleXMLElement($xml); 

$attr = $x->test[0]->a[0]->attributes(); 
echo $attr['a']; // "b" 

あなたはそれが「真」の配列になりたい場合は、ループに持っているつもりだ:

$attrArray = array(); 
$attr = $x->test[0]->a[0]->attributes(); 

foreach($attr as $key=>$val){ 
    $attrArray[(string)$key] = (string)$val; 
} 
+0

はい、問題はそれ自体がSimpleXML要素だと考えているため、正しく動作させるには '$ attr ['a']'を文字列に型変換する必要があります。私はこの配列を、どのような型であるかを知らない別のクラスに渡しているだけで、配列でなければなりません。 – mseancole

+0

ああ、あなたが編集でそれを持っています...ループは私が現在やっているものより "良い"ですか?私はループを使わないでこれを行うほうが速いと思うだろう。 – mseancole

+0

@showerhead:それが良いかどうかは分かりませんが、私はいつも ''@ attributes''プロパティを直接読まないことを学んできました。 –

0

私はあなたを介してループする必要がありますと思います。 xmlを読んだら、それを配列に入れることができます。

<?php 
function objectsIntoArray($arrObjData, $arrSkipIndices = array()) 
{ 
$arrData = array(); 

// if input is object, convert into array 
if (is_object($arrObjData)) { 
    $arrObjData = get_object_vars($arrObjData); 
} 

if (is_array($arrObjData)) { 
    foreach ($arrObjData as $index => $value) { 
     if (is_object($value) || is_array($value)) { 
      $value = objectsIntoArray($value, $arrSkipIndices); // recursive call 
     } 
     if (in_array($index, $arrSkipIndices)) { 
      continue; 
     } 
     $arrData[$index] = $value; 
    } 
} 
return $arrData; 
} 

$xmlStr = file_get_contents($xml_file); 
$xmlObj = simplexml_load_string($xmlStr); 
$arrXml = objectsIntoArray($xmlObj); 

foreach($arrXml as $attr) 
    foreach($attr as $key->$val){ 
if($key == '@attributes') .... 
} 
+1

'objectsIntoArray'とは何ですか?また、 '@属性 'を直接読むべきではありません。それは' - > attributes() 'のためのものです。 –

+0

申し訳ありませんが、私のコードから貼り付けられた部分が足りなくなってしまいました。 – PoX

40

もっとエレガントな方法。詳細については

$array = json_decode(json_encode((array) simplexml_load_string("<response>{$xml}</response>")), true); 

参照:

$attributes = current($element->attributes()); 
+0

絶対に単純でコンパクトで操作は少なくて済みます。 –

+0

@silverskater:非常に便利です、それは私のために働く!ありがとうございます –

+0

これは答えになるはずです – kfriend