PHP操作XML方法之SimpleXML


SimpleXML簡介

SimpleXML 擴展提供了一個非常簡單和易於使用的工具集,能將XML轉換成一個帶有一般屬性選擇器和數組迭代器的對象。

舉例XML

XML結構部分引用自<<深入理解PHP>>,並且為了說明某個方法的使用,強行增加一些看似根本用不合理的結構

我將用該XML結構完成:

<?xml version="1.0" encoding="utf-8"?>
<collection xmlns:lan="language">
    <php:book xmlns:php="php">
        <php:title php:edition="3">PHP Advanced and Object-Oriented Programming: Visual QuickPro Guide</php:title>
        <author:author xmlns:author="LarryUllman">Larry Ullman</author:author>
        <php:year>2012</php:year>
        <php:pages>612</php:pages>
        <php:chapterArr>
          <php:chapter php:number="12">PHP's Command-Line Interface</php:chapter>
          <php:chapter php:number="13">XML and PHP</php:chapter>
          <php:chapter php:number="14">Debugging, Testing, and Performance</php:chapter>
        </php:chapterArr>
        <php:cover php:fileName="phpvqp3.jpg"/>
    </php:book>
    <js:book xmlns:js="javascript">
        <js:title>Modern JavaScript: Develop and Design</js:title>
        <author:author  xmlns:author="LarryUllman">Larry Ullman</author:author>
        <js:year>2012</js:year>
        <js:pages>504</js:pages>
        <js:chapterArr>
          <js:chapter js:number="1" js:pages="24">(Re-)Introducing JavaScript</js:chapter>
          <js:chapter js:number="2" js:pages="32">JavaScript in Action</js:chapter>
          <js:chapter js:number="3" js:pages="34">Tools of the Trade</js:chapter>
        </js:chapterArr>
    </js:book>
</collection>

類方法及函數

在實際操作(增,刪,改,查)XML前,先簡單介紹一下SimpleXML包含的方法和函數對應的功能,如果你對此有一定的了解,可以跳本部分,直接看:生成XML操作讀取XML操作更新XML操作刪除XML操作的例子。

** PS:本文不會對方法和函數的功能及參數做詳細介紹(因為都已盡量體現在操作中),如想了解更多,請參考官網。 **

方法

  • addAttribute 為SimpleXML元素添加一個屬性
  • addChild 為SimpleXML節點增加一個子節點
  • asXML 返回一個基於SimpleXML對象沒有語法錯誤的XML字符串
  • attributes 識別元素的的所有屬性
  • children 返回給定節點的子節點
  • __construct 創建SimpleXML對象的初始化方法
  • count 計算元素子節點個數
  • getDocNamespaces 獲取XML文檔中申明的命名空間
  • getName 獲取SimpleXML節點的元素名
  • getNamespaces 獲取XML文檔中使用過的命名空間
  • registerXPathNamespace 為XPath查詢創建一個前綴或者命名空間
  • saveXML asXML的別名
  • __toString 魔術方法,返回SimpleXML節點的字符串內容
  • xpath 運行一個xpath查詢

函數

  • simplexml_import_dom 把一個DOM對象轉換為一個SimpleXML對象
  • simplexml_load_file 把一個XML文件解析為一個SimpleXML對象
  • simplexml_load_string 把一個字符串解析為一個SimpleXML對象

SimpleXML操作XML

生成XML

<?php 
//定義數據
$bookArr = [
    [
        'book'  => [
            'value' => null,
            'attr'  => [
                'nsKey'     => 'program:xmlns:php',
                'nsVal'     => 'php',
            ],
        ],
        'title'     =>
        [
            'value' => 'PHP Advanced and Object-Oriented Programming: Visual QuickPro Guide',
            'attr'  => [
                'edition' => 3
            ]
        ],
        'author'    => 'Larry Ullman',
        'year'      => 2012,
        'pages'     => 612,
        'chapterArr'=>
        [
            [
                'value' => 'PHP&apos;s Command-Line Interface',
                'attr'  => ['number'=>12]
            ],
            [
                'value' => 'XML and PHP',
                'attr'  => ['number'=>13]
            ],
            [
                'value' => 'Debugging, Testing, and Performance',
                'attr'  => ['number'=>14]
            ],
        ],
        'cover'   => [
            'attr'    => ['fileName'=>'phpvqp3.jpg'],
        ]
    ],
    [
        'book'  => [
            'value'  => null,  
            'attr'   => [
                'nsKey' => 'program:xmlns:js',
                'nsVal' => 'javascript',
            ]
        ],
        'title'     => ['value'=>'Modern JavaScript: Develop and Design'],
        'author'    => 'Larry Ullman',
        'year'      => 2012,
        'pages'     => 504,
        'chapterArr'=> [
            [
                'value' => '(Re-)Introducing JavaScript',
                'attr'  => ['number'=>1, 'pages'=>24]
            ],
            [
                'value' => 'JavaScript in Action',
                'attr'  => [ 'number'=>2, 'pages'=>32]
            ],
            [
                'value' => 'Tools of the Trade',
                'attr'  => ['number'=>3,'pages'=>34]
            ]
        ]
    ]
];

//用一段字符串生成一個XML的root節點
$statement = '<?xml version="1.0" encoding="utf-8"?><collection xmlns:lan="language"></collection>';
$rootXML = simplexml_load_string($statement); //等價於 $rootXML = new SimpleXMLElement($statement);

foreach($bookArr as $book){
    //獲取數組中定義的節點的命名空間,如program:xmlns:php,則php為元素的前綴
    $tempPrefix = substr($book['book']['attr']['nsKey'],strpos($book['book']['attr']['nsKey'], ':') + 1);
    $prefix = $tempPrefix ? $tempPrefix . ':' : '';

    //為root節點添加一個帶有指定命名空間的book節點
    $bookNode = $rootXML->addChild($prefix.'book',$book['book']['value']);

    //定義book節點的命名空間及前綴
    $bookNode->addAttribute($book['book']['attr']['nsKey'],$book['book']['attr']['nsVal']);

    //為book節點添加一個帶有指定命名空間,指定值的title節點
    $titleNode = $bookNode->addChild($prefix.'title',$book['title']['value']);

    //為title節點增加指定命名空間及屬性
    if(!empty($book['title']['attr'])){
        foreach($book['title']['attr'] as $k => $v){
            $titleNode->addAttribute($prefix.$k,$v);
        }
    }

    //為book節點添加一個子節點author及值
    $authorNode = $bookNode->addChild('author',$book['author']);
    //為author節點設置命名空間及前綴
    $authorNode->addAttribute('program:xmlns:author','LarryUllman');

    //為book節點添加一個子節點year及值
    $bookNode->addChild($prefix.'year',$book['year']);

    //為book節點添加一個子節點pages及值
    $bookNode->addChild($prefix.'pages',$book['pages']);

    //為book節點增加一個指定命名空間的chapterArr節點
    $chapterArr = $bookNode->addChild($prefix.'chapterArr');

    //為chapterArr節點增加一個指定命名空間,指定值指定屬性的chapter節點
    if(!empty($book['chapterArr'])){
        foreach($book['chapterArr'] as $value){
            $chapterNode = $chapterArr->addChild($prefix.'chapter',$value['value']);
            if(!empty($value['attr'])) {
                foreach ($value['attr'] as $k => $v) {
                    $chapterNode->addAttribute($prefix . $k, $v);
                }
            }
        }
    }

    //為book節點增加一個子節點帶有指定命名空間的cover,並設置其屬性
    if(!empty($book['cover']['attr']['fileName'])){
        $coverNode = $bookNode->addChild($prefix.'cover',null);
        $coverNode->addAttribute($prefix.'fileName',$book['cover']['attr']['fileName']);
    }

}

//設置header頭
header('content-type:text/xml;');
//格式化輸出SimpleXML對象
$xmlStr = $rootXML->asXML(); //也可保存到文件 $rootXML->asXML('/path/to/filename.xml');
echo $xmlStr;


讀取XML

//給定XML
$xmlStr = <<<XML
<?xml version="1.0" encoding="utf-8"?>
<collection xmlns:lan="language">
    <php:book xmlns:php="php">
        <php:title php:edition="3">PHP Advanced and Object-Oriented Programming: Visual QuickPro Guide</php:title>
        <author:author xmlns:author="LarryUllman">Larry Ullman</author:author>
        <php:year>2012</php:year>
        <php:pages>612</php:pages>
        <php:chapterArr>
          <php:chapter php:number="12">PHP's Command-Line Interface</php:chapter>
          <php:chapter php:number="13">XML and PHP</php:chapter>
          <php:chapter php:number="14">Debugging, Testing, and Performance</php:chapter>
        </php:chapterArr>
        <php:cover php:fileName="phpvqp3.jpg"/>
    </php:book>
    <js:book xmlns:js="javascript">
        <js:title>Modern JavaScript: Develop and Design</js:title>
        <author:author  xmlns:author="LarryUllman">Larry Ullman</author:author>
        <js:year>2012</js:year>
        <js:pages>504</js:pages>
        <js:chapterArr>
          <js:chapter js:number="1" js:pages="24">(Re-)Introducing JavaScript</js:chapter>
          <js:chapter js:number="2" js:pages="32">XML and PHP</js:chapter>
          <js:chapter js:number="3" js:pages="34">Debugging, Testing, and Performance</js:chapter>
        </js:chapterArr>
    </js:book>
</collection>
XML;

$rootXML = simplexml_load_string($xmlStr,null,null,'js',true);////等價於 $rootXML = new SimpleXMLElement($xmlStr,null,false,'js',true);

$data = [];

foreach($rootXML->book as $book){

    $data[$key]['title']   = (string)$book->title; //title值
    $data[$key]['edition'] = (string)$book->title['edition'];//title的edition屬性值
    
    //獲取book節點下命名空間前綴為author的子節點
    $author = $book->children('author',true);//
    $data[$key]['author'] = (string)$author;//author值
    
    $data[$key]['year'] = (int)$book->year;//year值
    $data[$key]['pages'] = (int)$book->pages;//pages值

    //多種獲取屬性的方式 開始
    $i = 0;
    foreach($book->chapterArr[0] as $chapter) {
        $data[$key]['chapterArr'][$i]['value'] = (string)$chapter;//chapter值
        //獲取chapter節點的number,pages屬性
        foreach ($chapter->attributes('js', true) as $chapterKey => $chapterVal) {
            $data[$key]['chapterArr'][$i]['attr'][$chapterKey] = (int)$chapterVal;
        }
        //$data[$key]['chapterArr'][$i]['attr']['number'] = (int)$chapter['number'];//也可這么獲取number屬性
        //$data[$key]['chapterArr'][$i]['attr']['pages'] = (int)$chapter['pages'];//也可這么獲取pages屬性
        $i++;
    }

    /*
    //獲取chapterArr子節點個數,然后循環獲取值及屬性
    $chapterNum = $book->chapterArr[0]->count();
    for($i=0;$i<$chapterNum;$i++) {
        $data[$key]['chapterArr'][$i]['value'] = (string)$book->chapterArr->chapter[$i];chapter值
        $data[$key]['chapterArr'][$i]['attr']['number'] = (int)$book->chapterArr->chapter[$i]['number'];number屬性
        $data[$key]['chapterArr'][$i]['attr']['pages'] = (int)$book->chapterArr->chapter[$i]['pages'];pages屬性
    }
    */
    
    /*
    通過xpath獲取屬性
    $chapterArr = $bookNode->xpath('//js:book//js:chapterArr//js:chapter');
    $i=0;
    foreach($chapterArr as $k=>$v){
      $data[$key]['chapterArr'][$i]['value'] = (string)$v;
      foreach($attr = $v->attributes('js',true) as $k=>$v){
        $data[$key]['chapterArr'][$i]['attr'][$k] = (int)$v;
      }
      $i++;
    }
    */

    //多種獲取屬性的方式 結束
    
    //cover值
    $fileName = (string)($book->cover['fileName']) && $data[$key]['cover']['attr']['fileName'] = $fileName;
    
}

var_dump($data);die;

更新XML


//$xmlStr如上
$rootXML = simplexml_load_string($xmlStr,null,null,'js',true);////等價於 $rootXML = new SimpleXMLElement($xmlStr,null,false,'js',true);

//更新標題及chapter的值及屬性
$rootXML->book->title = 'modifyXML';
$chapterArrNode = $rootXML->book->chapterArr[0];
$i = 1;
foreach($chapterArrNode as $chapter){
    $chapter[0]           = 'chapter'.$i;//修改值
    $chapter['number'] = 'number'.$i;//修改number屬性
    $chapter['pages']  = 'pages'.$i;//修改pages屬性
    $i++;
}

//設置header頭
header('content-type:text/xml;');
//格式化輸出SimpleXML對象
$xmlStr = $rootXML->asXML(); //也可保存到文件 $rootXML->asXML('/path/to/filename.xml');
echo $xmlStr;

刪除XML

//$xmlStr如上
$rootXML = simplexml_load_string($xmlStr,null,null,'js',true);////等價於 $rootXML = new SimpleXMLElement($xmlStr,null,false,'js',true);

//刪除year
unset($rootXML->book->year);

//刪除最后chapter標簽
unset($rootXML->book->chapterArr[0]->chapter[2]);

//刪除第一個chapter的pages屬性
unset($rootXML->book->chapterArr[0]->chapter[0]['pages']);

//使用xpath刪除number為2的chapter標簽
$rootXML->registerXPathNamespace('js','javascript');
foreach($rootXML->xpath('//js:book//js:chapterArr//js:chapter[@js:number=2]') as $chapter2)
{
    unset($chapter2[0]);
}

//設置header頭
header('content-type:text/xml;');
$xmlStr = $rootXML->asXML(); //也可保存到文件 $rootXML->asXML('/path/to/filename.xml');
echo $xmlStr;


免責聲明!

本站轉載的文章為個人學習借鑒使用,本站對版權不負任何法律責任。如果侵犯了您的隱私權益,請聯系本站郵箱yoyou2525@163.com刪除。



 
粵ICP備18138465號   © 2018-2025 CODEPRJ.COM