PHP 7.4+ 废弃 XML 解析器,推荐 SimpleXML(轻量读取)与 DOMDocument(完整控制)配合使用:前者语法简洁但不可修改、不支持命名空间精确查询;后者功能全面但需手动处理编码、选项和实体。

PHP 7.4+ 已移除对 PHP 4 风格的 XML 解析器(如 xml_parse)的默认支持,而 SimpleXML 和 DOMDocument 是当前主流且必须掌握的两种方式——它们不是互斥替代关系,而是适用场景不同:前者轻量、易读,后者完整、可控。
SimpleXML 适合快速提取结构化数据,但不能修改或构建复杂文档
SimpleXML 把 XML 当成对象树来用,写法简洁,但有硬性限制:不支持命名空间混用时的精确查询(需手动处理前缀),无法直接设置 CDATA,也不允许在解析后动态添加属性(除非转成 DOM)。常见错误是误以为 ->children() 能跨层级取值,其实它只返回直接子节点。
- 用
simplexml_load_string()或simplexml_load_file()加载,失败返回false,务必检查 - 访问元素用箭头语法:
$xml->item[0]->title,注意索引从 0 开始且[0]不可省略(即使只有一个) - 含命名空间时,先用
getNamespaces()获取前缀映射,再用children('prefix', true)进入对应空间 - 若需修改内容(比如替换文本),必须用
asXML()输出后再重新加载,或转交DOM处理
DOMDocument 更底层,适合构建、验证、XSLT 或带 DTD 的 XML
DOMDocument 是 W3C 标准实现,能做 SimpleXML 做不了的事:插入注释、设置文档类型(doctype)、执行 XPath 查询、绑定 XSLT、处理实体引用。但它写法啰嗦,容易因编码或加载选项出错——比如默认不启用外部实体加载,导致 load() 对含 的文件静默失败。
- 创建新文档用
new DOMDocument('1.0', 'UTF-8'),编码必须显式声明,否则中文可能乱码 - 加载已有 XML 时,推荐加选项:
$dom->load($file, LIBXML_NOBLANKS | LIBXML_NOCDATA),避免空文本节点干扰遍历 - 查节点优先用
$xpath = new DOMXPath($dom)+$xpath->query(),比反复getElementsByTagName()更准更稳 - 写入时注意:用
$dom->saveXML()会输出声明头,用$dom->saveHTML()会转义特殊字符,按需选
两者互转是常用技巧,但要注意内存与编码陷阱
有时得先用 SimpleXML 快速读取,再转成 DOM 修改并保存。PHP 提供了 dom_import_simplexml() 和 simplexml_import_dom(),但转换过程不保留原始缩进,且如果源 XML 声明了编码(如 ),而 PHP 内部用 UTF-8 处理,就会出现乱码——必须在加载前用 mb_convert_encoding() 统一转码。
立即学习“PHP免费学习笔记(深入)”;
- 从
SimpleXML转DOM:$dom = dom_import_simplexml($sx)->ownerDocument(注意取ownerDocument,不是直接返回节点) - 修改后存回字符串:
$dom->saveXML($dom->documentElement)可去掉 XML 声明,避免重复头 - 若原始 XML 含 GBK 编码,先用
$xml_utf8 = mb_convert_encoding($xml_gbk, 'UTF-8', 'GBK')再解析
真正麻烦的不是语法,而是 XML 的隐式规则:编码声明是否真实生效、DTD 是否被禁用、命名空间是否被正确继承、外部实体是否被解析——这些在 SimpleXML 里被隐藏,在 DOMDocument 里则需要你主动控制 libxml 的选项。没踩过 LIBXML_DTDLOAD 和 LIBXML_NOENT 的坑,就不算真用过 PHP 解析 XML。








