Зацикливание на объекте SimpleXML или превращение всего объекта в массив

StackOverflow https://stackoverflow.com/questions/871422

Вопрос

Я пытаюсь понять, как выполнить итерацию через возвращаемый объект SimpleXML.

Я использую инструментарий под названием Тарзан AWS, который подключается к Amazon Web Services (SimpleDB, S3, EC2 и т.д.).Я специально использую SimpleDB.

Я могу поместить данные в сервис Amazon SimpleDB и получить их обратно.Я просто не знаю, как обращаться с возвращаемым объектом SimpleXML.

В документации Tarzan AWS говорится следующее:

Посмотрите на ответ, чтобы перейти по заголовкам и телу ответа.Обратите внимание, что это объект, а не массив, и что тело является объектом SimpleXML.

Вот пример возвращенного объекта SimpleXML:

 [body] => SimpleXMLElement Object
        (
            [QueryWithAttributesResult] => SimpleXMLElement Object
                (
                    [Item] => Array
                        (
                            [0] => SimpleXMLElement Object
                                (
                                    [Name] => message12413344443260
                                    [Attribute] => Array
                                        (
                                            [0] => SimpleXMLElement Object
                                                (
                                                    [Name] => active
                                                    [Value] => 1
                                                )

                                            [1] => SimpleXMLElement Object
                                                (
                                                    [Name] => user
                                                    [Value] => john
                                                )

                                            [2] => SimpleXMLElement Object
                                                (
                                                    [Name] => message
                                                    [Value] => This is a message.
                                                )

                                            [3] => SimpleXMLElement Object
                                                (
                                                    [Name] => time
                                                    [Value] => 1241334444
                                                )

                                            [4] => SimpleXMLElement Object
                                                (
                                                    [Name] => id
                                                    [Value] => 12413344443260
                                                )

                                            [5] => SimpleXMLElement Object
                                                (
                                                    [Name] => ip
                                                    [Value] => 10.10.10.1
                                                )

                                        )

                                )

                            [1] => SimpleXMLElement Object
                                (
                                    [Name] => message12413346907303
                                    [Attribute] => Array
                                        (
                                            [0] => SimpleXMLElement Object
                                                (
                                                    [Name] => active
                                                    [Value] => 1
                                                )

                                            [1] => SimpleXMLElement Object
                                                (
                                                    [Name] => user
                                                    [Value] => fred
                                                )

                                            [2] => SimpleXMLElement Object
                                                (
                                                    [Name] => message
                                                    [Value] => This is another message
                                                )

                                            [3] => SimpleXMLElement Object
                                                (
                                                    [Name] => time
                                                    [Value] => 1241334690
                                                )

                                            [4] => SimpleXMLElement Object
                                                (
                                                    [Name] => id
                                                    [Value] => 12413346907303
                                                )

                                            [5] => SimpleXMLElement Object
                                                (
                                                    [Name] => ip
                                                    [Value] => 10.10.10.2
                                                )

                                        )

                                )

                        )

Итак, какой код мне нужен, чтобы пройти через каждый из элементов объекта?Я бы хотел перебрать каждый из них и обработать его как возвращенный запрос MySQL.Например, я могу запросить SimpleDB, а затем выполнить цикл через SimpleXML, чтобы отобразить результаты на странице.

В качестве альтернативы, как вы превращаете весь shebang в массив?

Я новичок в SimpleXML, поэтому приношу извинения, если мои вопросы недостаточно конкретны.

Это было полезно?

Решение

Вы можете использовать SimpleXML объект (или его свойства) в foreach петля.Если вы хотите просмотреть все "записи", что-то вроде этого можно использовать для доступа к данным и их отображения:

//Loop through all the members of the Item array 
//(essentially your two database rows).
foreach($SimpleXML->body->QueryWithAttributesResult->Item as $Item){
    //Now you can access the 'row' data using $Item in this case 
    //two elements, a name and an array of key/value pairs
    echo $Item->Name;
    //Loop through the attribute array to access the 'fields'.
    foreach($Item->Attribute as $Attribute){
        //Each attribute has two elements, name and value.
        echo $Attribute->Name . ": " . $Attribute->Value;
    }
}

Обратите внимание, что $Item будет объектом SimpleXML, как и $Attribute, поэтому на них нужно ссылаться как на объекты, а не как на массивы.

В то время как приведенный выше пример кода выполняет цикл по массивам в объекте SimpleXML ($SimpleXML->body->QueryWithAttributesResult->Item), вы также можете выполнить цикл по объекту SimpleXML (скажем, $SimpleXML->body->QueryWithAttributesResult->Item[0]), и это даст вам каждое из свойств объекта.

Каждый дочерний элемент объекта SimpleXML является XML-сущностью.Если XML-объект (тег) не уникален, то элемент представляет собой просто массив объектов SimpleXML, представляющих каждый объект.

Если вы хотите, это должно создать более общий массив строк / полей из вашего объекта SimpleXML (или приблизить вас):

foreach($SimpleXML->body->QueryWithAttributesResult->Item as $Item){
    foreach($Item->Attribute as $Attribute){
        $rows[$Item->Name][$Attribute->Name] = $Attribute->Value;
    }
}

//Now you have an array that looks like:
$rows['message12413344443260']['active'] = 1;
$rows['message12413344443260']['user'] = 'john';
//etc.

Другие советы

get_object_vars($simpleXMLElement);

одно небольшое дополнение для исправления PHP 5.2.

$response_array = json_decode(json_encode($response),true);

В случае XML-ответов, которые НЕ содержат разделов CDATA (например, Amazon / Tarzan), вы можете использовать следующее, предполагая, что у вас PHP 5.2 или новее.

// Get a SimpleXML response back from Tarzan
$s3 = new AmazonS3();
$response = $s3->list_buckets();

// Convert SimpleXML to Array in PHP 5.2.
$response_array = json_decode(json_encode($response));

Это будет стандартная утилита, доступная для всех объектов в следующей основной версии Tarzan (CloudFusion 2.5).

Почти все примеры, которые я нашел, относятся к конкретному примеру, где вы уже знаете узлы.Следующая функция преобразует SimpleXMLElement в массив, не зная имен узлов и того, есть ли у них дочерние элементы или нет.Также будет отлично работать с разделами CDATA.

function parseXML(SimpleXMLElement $xml) : array
{
    $array = [];

    foreach(iterator_to_array($xml, TRUE) as $key => $value)
        $array[$key] = ($value->count() > 1) ? parseXML($value) : (string)$value;

    return $array;
}

Это сработало:

// $result is a Simple XML object

$result = convertSimpleXMLToArray($result);

function convertSimpleXMLToArray($xml)
{
    if(class_basename($xml) == 'SimpleXMLElement')
    {
        $xml = get_object_vars($xml);
        foreach($xml as $key => $value)
        {
            if(class_basename($value) == 'SimpleXMLElement') $xml[$key] = convertSimpleXMLToArray($value);
        }
    }

    return $xml;
}
Лицензировано под: CC-BY-SA с атрибуция
Не связан с StackOverflow
scroll top