PHP XML

Expat (SAX) parser functions and error handling.

Intermediate
Key PointsWhen `xml_parse` returns `false`, check `xml_get_error_code`.

Functions

FunctionPurpose
xml_parser_create创建解析器(指定输出编码)
xml_parser_free释放解析器
xml_parse喂数据(第三参数标最后一块)
xml_parse_into_struct一次解析成数组
xml_set_element_handler开始/结束标签回调
xml_set_character_data_handler文本回调
xml_set_default_handler默认回调(注释、CDATA 等)
xml_get_error_code错误码
xml_error_string错误描述
xml_get_current_line_number出错行号
xml_parser_set_option设置选项(大小写折叠等)

Parse into an array

PHP
<?php
$xml = '<r><a id="1">x</a><b>y</b></r>';

$p = xml_parser_create("UTF-8");
xml_parse_into_struct($p, $xml, $vals, $index);
xml_parser_free($p);

print_r($vals[1]);
echo $index["A"][0], "\n";
Output
Array
(
    [tag] => A
    [attributes] => Array
        (
            [ID] => 1
        )

    [type] => complete
    [level] => 2
    [value] => x
)
1

$vals is a flat event list and $index maps tag names to positions. It saves writing callbacks for simple XML.

Locating errors

PHP
<?php
$xml = "<r>\n  <a>1</a>\n  <b>2</c>\n</r>";

$p = xml_parser_create("UTF-8");

$ok = xml_parse($p, $xml, true);

if (!$ok) {
    echo "错误码: " . xml_get_error_code($p) . "\n";
    echo "描述: " . xml_error_string(xml_get_error_code($p)) . "\n";
    echo "行号: " . xml_get_current_line_number($p) . "\n";
    echo "列号: " . xml_get_current_column_number($p) . "\n";
}

xml_parser_free($p);
Output
错误码: 76
描述: Mismatched tag
行号: 3
列号: 11
Codes come from libxml and should not be hardcoded — they can change between versions. Use xml_error_string() or just the boolean.

Options

PHP
<?php
$xml = '<Root><Item id="1">A</Item></Root>';

$p = xml_parser_create("UTF-8");
xml_parser_set_option($p, XML_OPTION_CASE_FOLDING, 0);
xml_parser_set_option($p, XML_OPTION_TARGET_ENCODING, "UTF-8");

xml_set_element_handler(
    $p,
    function ($p, $name, $attrs) {
        echo "标签: $name\n";
    },
    function ($p, $name) {}
);

xml_parse($p, $xml, true);
xml_parser_free($p);
Output
标签: Root
标签: Item

SAX or DOM

NeedSAXDOM
内存恒定是否
随机访问节点否是
修改文档困难容易
代码复杂度高低
大文件适合不适合
SAX code is typically 3× longer than DOM and its state handling is error-prone. Only worth it when the file is too big for DOM.

Friends & Partners