children()
Узнайте, как PHP-метод SimpleXMLElement::children() возвращает прямые дочерние элементы XML-узла с фильтрацией по пространству имён через $ns и $is_prefix.
Введение
SimpleXMLElement::children() возвращает прямые дочерние элементы XML-узла в виде нового объекта SimpleXMLElement. Этот метод входит в состав расширения SimpleXML для PHP — лёгкого объектно-ориентированного способа чтения и обхода XML. К children() обращаются тогда, когда нужно перебрать или подсчитать элементы, непосредственно вложенные в узел, не обращаясь к каждому из них по имени тега.
На этой странице рассматриваются сигнатура метода и возвращаемое значение, способы перебора дочерних элементов, их подсчёта, а также тема, которую большинство руководств обходит стороной: чтение элементов, расположенных в пространстве имён XML.
Синтаксис
public SimpleXMLElement::children(?string $namespace = null, bool $isPrefix = false): ?SimpleXMLElement| Параметр | Описание |
|---|---|
$namespace | Необязательный. Пространство имён XML для фильтрации дочерних элементов. Если не указан, возвращаются элементы из пространства имён по умолчанию. |
$isPrefix | Необязательный. Если true, параметр $namespace трактуется как префикс пространства имён (например, lib); если false (значение по умолчанию) — как URI пространства имён (например, http://example.com/lib). |
Возвращаемое значение: объект SimpleXMLElement, по которому можно итерировать с помощью foreach, обращаться к элементам по индексу как к массиву ($children[0]) или передавать в count(). Возвращает null только при вызове на объекте, не являющемся допустимым элементом.
children()возвращает только прямые дочерние элементы — вглубь, к внукам, метод не спускается. Чтобы добраться до более глубоких узлов, вызовитеchildren()повторно на дочернем элементе или воспользуйтесь XPath.
Перебор дочерних элементов
Наиболее распространённый сценарий — перебор всех прямых дочерних элементов узла в цикле:
Вывод:
PHP Basics - John Doe
Mastering XML - Jane RoeЗдесь $xml — это корневой элемент <books>, а children() возвращает каждый <book>. Внутри цикла $book->title и $book->author читают значения элементов-внуков. Поскольку оба элемента <book> имеют одно и то же имя тега, цикл — самый естественный способ обработки повторяющейся структуры.
Подсчёт дочерних элементов
Возвращаемый объект поддерживает функцию count(), поэтому можно проверить количество прямых дочерних элементов узла и обращаться к ним по индексу как к массиву:
<?php
$xml = new SimpleXMLElement('<menu><item>Tea</item><item>Coffee</item><item>Juice</item></menu>');
$children = $xml->children();
echo "Number of items: ", count($children), "\n";
echo "First item: ", $children[0], "\n";Вывод:
Number of items: 3
First item: TeaРабота с пространствами имён
Именно здесь параметры children() раскрывают свою ценность. Когда документ использует пространства имён XML, обычный вызов children() без аргументов возвращает только элементы пространства имён по умолчанию — элементы с префиксами при этом пропускаются. Чтобы получить к ним доступ, необходимо передать пространство имён.
<?php
$xml = new SimpleXMLElement(
'<library xmlns:lib="http://example.com/lib">
<lib:book>Namespaced Book</lib:book>
<note>Plain note</note>
</library>'
);
// No namespace: only children in the default namespace
echo count($xml->children()), " default-namespace child(ren)\n";
// Pass the namespace URI to reach the lib: children
$libChildren = $xml->children('http://example.com/lib');
echo count($libChildren), " lib child(ren): ", trim((string) $libChildren->book), "\n";
// Or pass the prefix with $isPrefix = true
$byPrefix = $xml->children('lib', true);
echo count($byPrefix), " child(ren) by prefix\n";Вывод:
1 default-namespace child(ren)
1 lib child(ren): Namespaced Book
1 child(ren) by prefixОбратите внимание: вызов children() без аргументов находит только <note>, тогда как children('http://example.com/lib') — элемент <lib:book>. Если об этом забыть, данные с пространством имён словно «исчезают» — классическая ловушка SimpleXML.
Типичные ошибки
- Возвращаются только прямые дочерние элементы. Для доступа к внукам нужен ещё один вызов
children()или использование XPath. - Элементы с пространством имён требуют соответствующего аргумента. Вызов
children()без аргументов молча игнорирует элементы с префиксами. - Значения являются объектами, а не строками. Листовой узел необходимо привести к string (
(string) $child) или включить его в конкатенацию, прежде чем использовать как текст. - Атрибуты возвращаются отдельно.
children()возвращает вложенные элементы; для чтения атрибутов элемента используйтеattributes().
Заключение
SimpleXMLElement::children() — стандартный способ перечисления прямых дочерних элементов XML-узла в PHP: будь то перебор в цикле foreach, подсчёт с помощью count() или обращение к конкретному пространству имён через параметры $namespace и $isPrefix. Сочетайте этот метод с attributes() и simplexml_load_string() для чистого разбора реальных XML-документов.