downloads | documentation | faq | getting help | mailing lists | licenses | wiki | reporting bugs | php.net sites | links | conferences | my php.net

search for in the

SimpleXMLElement::__construct> <SimpleXMLElement::attributes
Last updated: Fri, 20 May 2011

view this page in

SimpleXMLElement::children

(PHP 5 >= 5.0.1)

SimpleXMLElement::childrenEncuentra los hijos del nodo dado

Descripción

public SimpleXMLElement SimpleXMLElement::children ([ string $ns [, bool $is_prefix = false ]] )

Este método encuentra el hijo de un elemento. El resultado cumple las reglas normales de iteración.

Note: SimpleXML ha desarrollado una regla para el añadido de propiedades iterativas a la mayoría de métodos. No pueden ser examinados usando var_dump() ni con cualquier otra función que examine objetos.

Parámetros

ns

Un nombre de espacio XML.

is_prefix

Si is_prefix es TRUE, ns será considerado como un prefijo. Si es FALSE ns será considerado como un espacio de nombres URL.

Valores devueltos

Devuelve un elemento SimpleXMLElement, tanto si el nodo tiene hijos o no.

Historial de cambios

Versión Descripción
5.2.0 Se añade el parámetro opcional is_prefix.

Ejemplos

Example #1 Recorre el pseudo-array children()

<?php
$xml 
= new SimpleXMLElement(
'<persona>
 <hijo rol="hijo">
  <hijo rol="hija"/>
 </hijo>
 <hijo rol="hija">
  <hijo rol="hijo">
   <hijo rol="hijo"/>
  </hijo>
 </hijo>
</persona>'
);

foreach (
$xml->children() as $segunda_gen) {
    echo 
'La persona engendra un/a ' $segunda_gen['role'];

    foreach (
$second_gen->children() as $tercera_gen) {
        echo 
' quien engendra un/a ' $tercera_gen['role'] . ';';

        foreach (
$tercera_gen->children() as $cuarta_gen) {
            echo 
' y ese/a ' $tercera_gen['role'] .
                
' engendra un/a ' $cuarta_gen['role'];
        }
    }
}
?>

El resultado del ejemplo sería:

La persona engendra un/a hijo quien engendra un/a hija; La persona engendra
un/a hija quien engendra a un/a hijo; y ese/a hijo engendra un/a hijo

Example #2 Usando espacio de nombres

<?php
$xml 
'<example xmlns:foo="my.foo.urn">
  <foo:a>Apple</foo:a>
  <foo:b>Banana</foo:b>
  <c>Cherry</c>
</example>'
;

$sxe = new SimpleXMLElement($xml);

$kids $sxe->children('foo');
var_dump(count($kids));

$kids $sxe->children('foo'TRUE);
var_dump(count($kids));

$kids $sxe->children('my.foo.urn');
var_dump(count($kids));

$kids $sxe->children('my.foo.urn'TRUE);
var_dump(count($kids));

$kids $sxe->children();
var_dump(count($kids));
?>
int(0)
int(2)
int(2)
int(0)
int(1)

Notas

SimpleXMLElement::children() devuleve un nodo de objeto no impotando si el nodo actuali tiene un hijo o no. Use SimpleXMLElement::count() en el valor retornado para comprobar si hay algún hijo. Como en PHP 5.3.0, SimpleXMLElement::count() puede usarse en su lugar.

Ver también



add a note add a note User Contributed Notes SimpleXMLElement::children
coldshine1 at rambler dot ru 10-Dec-2010 10:37
This is my recursive simple function to parse XML with attributes.

<?php
function ParseXML($node, &$parent=array(), $only_child=true) {        

       
//Current node name
       
$node_name = $node->getName();
         
       
//Let's count children
       
$only_child = true;
        if(
$node->count() > 1 ) $only_child = false;

       
//If there is no child, then there may be text data
       
if($only_child){
           
$content="$node";           
            if (
strlen($content)>0) $parent['content']=$content;
        }
       
       
//Get attributes of current node
       
foreach ($node->attributes() as $k=>$v) {
           
$parent['@attributes'][$k]="$v";
        }
      
       
//Get children
       
$count = 0;
        foreach (
$node->children() as $child_name=>$child_node) {
            if(!
$only_child) //If there are siblings then we'll add node to the end of the array
               
LGServerPVR::ParseXML($child_node, $parent[$node_name][$child_name][$count], $only_child);
            else
               
LGServerPVR::ParseXML($child_node, $parent[$node_name][$child_name], $only_child);
           
$count++;
        }
       
        return
$parent
       
//(c) c01d[s]h!nE 10.12.2010      
   
}

?>
Anonymous 26-Oct-2010 12:19
Here's my xml-to-array routine. Unlike many of the other comments here, this one takes namespaces into account.

<?php

class XmlArray {

  public function
load_dom ($xml) {
   
$node=simplexml_import_dom($xml);
    return
$this->add_node($node);
  }
 
  public function
load_string ($s) {
   
$node=simplexml_load_string($s);
    return
$this->add_node($node);
  }
 
  private function
add_node ($node, &$parent=null, $namespace='', $recursive=false) {
 
   
$namespaces = $node->getNameSpaces(true);
   
$content="$node";
   
   
$r['name']=$node->getName();
    if (!
$recursive) {
     
$tmp=array_keys($node->getNameSpaces(false));
     
$r['namespace']=$tmp[0];
     
$r['namespaces']=$namespaces;
    }
    if (
$namespace) $r['namespace']=$namespace;
    if (
$content) $r['content']=$content;
   
    foreach (
$namespaces as $pre=>$ns) {
      foreach (
$node->children($ns) as $k=>$v) {
       
$this->add_node($v, $r['children'], $pre, true);
      }
      foreach (
$node->attributes($ns) as $k=>$v) {
       
$r['attributes'][$k]="$pre:$v";
      }
    }
    foreach (
$node->children() as $k=>$v) {
     
$this->add_node($v, $r['children'], '', true);
    }
    foreach (
$node->attributes() as $k=>$v) {
     
$r['attributes'][$k]="$v";
    }
   
   
$parent[]=&$r;
    return
$parent[0];
   
  }

}

?>
alan at performantsystems dot com 11-Aug-2010 09:40
As I have occasion to retrieve a single data item rather than a list, I wanted a way to just grab and parse one data item from XML.  Here is one way to do that:

<?php
echo "\n";
$XML =
'<data>
   <USERS>
      <ID>alang</ID>
      <NAME>Alan Gruskoff</NAME>
      <ROLE>mgr</ROLE>
   </USERS>
</data>'
;

$xmlObject = new SimpleXMLElement($XML);

$node = $xmlObject->children();
echo
"var_dump node\n";
var_dump($node);
echo
"\n";

echo
"\nnode ID=". $node[0]->ID;
echo
"\nnode NAME=". $node[0]->NAME;
echo
"\nnode ROLE=". $node[0]->ROLE;

echo
"\n";
?>

This will show the contents of the $node child of the $xmlObject and then the specific element values.
php at shiinaringo dot se 18-Feb-2010 10:42
Most examples on this page do not take namespaces into account, rendering them useless in many cases. Here is a function to convert xml to array. You have to feed it the list of namespaces to use. Watch the example at the bottom.

<?php

function xml2phpArray($xml, $namespaces, $arr) {
   
$iter = 0;

    foreach (
$namespaces as $namespace => $namespaceUrl) {
        foreach (
$xml->children($namespaceUrl) as $b) {
           
$a = $b->getName();

            if (
$b->children($namespaceUrl)) {
               
$arr[$a][$iter] = array();
               
$arr[$a][$iter] = xml2phpArray($b, $namespaces, $arr[$a][$iter]);
            }
            else {
               
$arr[$a] = trim($b[0]);
            }

           
$iter++;
        }
    }

    return
$arr;
}

$xml = simplexml_load_file('http://urltosomexmlfile.xml');

$namespaces = array_merge(array('' => ''), $xml->getDocNamespaces(true));
$myArray = array();
$myArray = xml2phpArray($xml, $namespaces, $myArray);

?>
mrdaniellee at live dot com 10-Jan-2010 05:11
use this If you want to view the HTML as well as data.

normal dumps display the parsed versions of HTML.
This code displays the HTML as Text in a Text Area, and also display all other a data along side as an array

perfect for debugging (xml with html).

Try This Code:

<?php
$xml 
= simplexml_load_file($url);

function
xml2array_parse($xml){
     foreach (
$xml->children() as $parent => $child){
        
$return["$parent"] = xml2array_parse($child)?xml2array_parse($child):"$child";
     }
     return
$return;
 }
 
 print
"<pre><textarea style=\"width:200%;height:100%;\">";
 
print_r(xml2array_parse($xml));
 print
"</textarea></pre>";
?>
rodmen at gmail dot com 21-May-2009 03:32
Transform xml to array php

<?php
function xml2phpArray($xml,$arr){
   
$iter = 0;
        foreach(
$xml->children() as $b){
               
$a = $b->getName();
                if(!
$b->children()){
                       
$arr[$a] = trim($b[0]);
                }
                else{
                       
$arr[$a][$iter] = array();
                       
$arr[$a][$iter] = xml2phpArray($b,$arr[$a][$iter]);
                }
       
$iter++;
        }
        return
$arr;
}

$Array = simplexml_load_string(file_get_contents('myfile.xml'));
print_r(xml2phpArray($Array,array()));
?>
G dot B dot Yahav at Gmail dot com 25-Mar-2009 06:26
I done a very nice function to run over the XML element recursivly with SimpleXML, and print it on the screen

here it is:

<?php

$xml_han
= new SimpleXMLElement( "data.xml", null, true );

print
RecursiveXML( $xml_han );
function
RecursiveXML( SimpleXMLElement $han, $preffix = "")
{
    if(
count( $han->children() ) < 1 )
    {
        return
$preffix . "&lt;" . $han->getName() . warpAttributes( $han->attributes() ) . "&gt;&nbsp;" . $han . "&nbsp;&lt;/" . $han->getName() . "&gt;<br />";
    }
   
   
$ret = $preffix . "&lt;" . $han->getName() . warpAttributes( $han->attributes() ) . "&gt;<br />";
    foreach(
$han->children() as $key => $child )
    {
       
$ret .= RecursiveXML($child , $preffix . "|--&nbsp;&nbsp;&nbsp;" );
    }
    return
$ret;
}

?>

enjoy :)
hoseinnj at google&#39;s great mail dot com 19-Mar-2009 07:25
Quick easy way to turn objectified SimpleXMLElement data into an array.

<?php
function get_xml_from_some_source(){
//blah blah blah build cUrl
$data = @curl_exec($ch);
$newdata = new SimpleXMLElement($data);
$new = xml2array_parse($newdata);
}

function
xml2array_parse($xml){
     foreach (
$xml->children() as $parent => $child){
        
$return["$parent"] = xml2array_parse($child)?xml2array_parse($child):"$child";
     }
     return
$return;
 }
?>

My first post, be nice.  ;-)
Anonymous 06-Sep-2008 12:39
for XML namespaces such as <dc:creator> in RSS feeds use

<?php
    $xml
= new SimpleXMLElement($string);
   
$item = $xml->channel[0]->item[0];
   
$dc = $item->children("http://purl.org/dc/elements/1.1/");
    echo
$dc->creator;
?>
transglobe at gmx dot de 19-Mar-2008 10:37
I made a slightly differnt approch towards the RecurseXML function. Beeing hungry I had problems with the code, as it did just overwrite two <maincourse>s. So here is what I did:

<?php

$xml
= new SimpleXMLElement(
'<meal>
   <type>Lunch</type>
   <time>12:30</time>
   <menu>
     <entree>salad</entree>
     <maincourse>
        <part>ships</part>
        <part>steak</part>
     </maincourse>
     <maincourse>
        <part>fisch</part>
        <part>rice</part>
     </maincourse>
     <maincourse>
        <part>wine</part>
        <part>cheese</part>
     </maincourse>
   </menu>
</meal>'
);

$vals = array();
RecurseXML($xml,$vals);

foreach(
$vals as $key=>$value)
  print(
"{$key} = {$value}<BR>\n");

function
RecurseXML($xml,&$vals,$parent="") {

 
$childs=0;
 
$child_count=-1; # Not realy needed.
 
$arr=array();
        foreach (
$xml->children() as $key=>$value) {
                if (
in_array($key,$arr)) {
                       
$child_count++;
                } else {
                       
$child_count=0;
                }
               
$arr[]=$key;
               
$k=($parent == "") ? "$key.$child_count" : "$parent.$key.$child_count";
               
$childs=RecurseXML($value,$vals,$k);
                if (
$childs==0) {
                       
$vals[$k]= (string)$value;
                }
        }

  return
$childs;
}

?>
Output is like this:
type.0 = Lunch
time.0 = 12:30
menu.0.entree.0 = salad
menu.0.maincourse.0.part.0 = ships
menu.0.maincourse.0.part.1 = steak
menu.0.maincourse.0 =
menu.0.maincourse.1.part.0 = fisch
menu.0.maincourse.1.part.1 = rice
menu.0.maincourse.1 =
menu.0.maincourse.2.part.0 = wine
menu.0.maincourse.2.part.1 = cheese
menu.0.maincourse.2 =
menu.0 =

(Not beautiful, but it solved my case...)
crescentfreshpot at yahoo dot com 10-Dec-2007 04:16
Just a warning that the iterable returned from children() contains the '@attributes' key, which is "invisible" during a foreach but can be seen if using a different construct, such as list()=each() or casting to an array before iterating w/ foreach.
aero 23-May-2007 03:07
Here's a simple, recursive, function to transform XML data into pseudo E4X syntax ie. root.child.value = foobar

<?php
error_reporting
(E_ALL);

$xml = new SimpleXMLElement(
'<Patriarch>
   <name>Bill</name>
   <wife>
     <name>Vi</name>
   </wife>
   <son>
     <name>Bill</name>
   </son>
   <daughter>
     <name>Jeri</name>
     <husband>
       <name>Mark</name>
     </husband>
     <son>
       <name>Greg</name>
     </son>
     <son>
       <name>Tim</name>
     </son>    
     <son>
       <name>Mark</name>
     </son>    
     <son>
       <name>Josh</name>
         <wife>
           <name>Kristine</name>
         </wife>
         <son>
           <name>Blake</name>
         </son>
         <daughter>
           <name>Liah</name>
         </daughter>
     </son>
   </daughter>
</Patriarch>'
);

RecurseXML($xml);

function
RecurseXML($xml,$parent="")
{
  
$child_count = 0;
   foreach(
$xml as $key=>$value)
   {
     
$child_count++;    
      if(
RecurseXML($value,$parent.".".$key) == 0// no childern, aka "leaf node"
     
{
         print(
$parent . "." . (string)$key . " = " . (string)$value . "<BR>\n");       
      }    
   }
   return
$child_count;
}

?>

The output....

.name = Bill
.wife.name = Vi
.son.name = Bill
.daughter.name = Jeri
.daughter.husband.name = Mark
.daughter.son.name = Greg
.daughter.son.name = Tim
.daughter.son.name = Mark
.daughter.son.name = Josh
.daughter.son.wife.name = Kristine
.daughter.son.son.name = Blake
.daughter.son.daughter.name = Liah
taylorbarstow at that google mail thingy 21-Apr-2006 02:38
Sometimes you actually want an array, not a pseudo array.   This is especially true when you aren't dealing with attributes (i.e., you just want the array of child nodes).

Do like this:

<?php
$children
= $sxml->xpath('child::node()');
?>

The reason you might want this is to be able to use array functions like array_shift, array_pop, etc.  This is especially true when you are writing recursive functions.  Simplexml works really well in iterative programming, but if you try to implement recursion it gets ugly.
Sebastian 27-Oct-2005 10:45
Just a quick addition:

If you need to access a child node which contains a dash, you need to encapsulate it with {""}.

For example:
<?php
foreach ($domain->domain-listing as $product) {
}
?>

The example above doesn't work because of the dash. But instead you need to use:
<?php
foreach ($domain->{"domain-listing"} as $product) {
}
?>

At least for me the second example works perfectly fine.
no-one 01-Jun-2005 01:05
For anyone who hasn't read Sterling Hughe's article (http://www.zend.com/php5/articles/php5-simplexml.php):

<?php
$xml_document
=<<<EOT
<?xml version="1.0"?>
<root xmlns:foo="http://example.com">
  <foo:bar>baz</foo:bar>
</root>
EOT;

$xml_document = simplexml_load_xml($xml_document);

$foo_ns_bar = $xml_document->children('http://example.com');

echo
$foo_ns_bar->bar[0]; // prints 'baz'
?>
Andrew Rose (rose dot andrew at gmail dot com) 16-Mar-2005 12:48
The example below shows the basic use of depth-first recursion to span the xml tree.

This is coded for the command line, and it prints out the original sentance above and then the copy cat sentence it creates itself for comparison, which as you will see; this example is slightly off from, I'll leave it upto you to resolve this issue.

All in all I personaly think xml and recursion go hand in hand, so if you don't understand recursion but know xml and want to use php to manipulate xml you will need to learn about recursion at some point.

<?php
$xml
= simplexml_load_string(
'<person>
 <child role="son">
  <child role="daughter"/>
 </child>
 <child role="daughter">
  <child role="son">
   <child role="son"/>
  </child>
 </child>
</person>'
);

function
recurse($child)
 {
   foreach(
$child->children() as $children) {
     echo
' who begot a '.$children['role'];
    
recurse($children);
   }
    return;
 }

foreach(
$xml->children() as $children) {
 echo
'The person begot a '.$children['role'];
 
recurse($children, 0);
 echo
'; ';
}

echo
"\n";
echo
'The person begot a son who begot a daughter; The person begot a daughter who begot a son; and that son begot a son'."\n";

?>
zyxwvu at users dot sourceforge dot net 15-Feb-2004 06:32
File:

<category>
  <item>text</item>
  <bold>text</bold>
  <item>text</item>
  <item>text</item>
  <mark>text</mark>
  <bold>text</bold>
</category>

If you want to get also names of the tags, you can use this loop layout:

<?php
foreach($category -> children() as $name => $node){
  echo
$name.'<br/>';
}
?>

 
show source | credits | stats | sitemap | contact | advertising | mirror sites