1、前言
XML树状层次结构鲜明,非常适合作为配置文件。PHP中可以使用DOM XML来操作XML。本文总结一下PHP使用DOM XML创建、添加节点、查询XML文件。
2、使用DOM XML
XML中节点分为元素和文本,DOMDocument类型是文档类型,提供了操作元素和文本的成员函数和属性。
DOMDocument类如下:
DOMDocument extends DOMNode {
/* Properties */
readonly public string $actualEncoding ;
readonly public DOMConfiguration $config ;
readonly public DOMDocumentType $doctype ;
readonly public DOMElement $documentElement ;
public string $documentURI ;
public string $encoding ;
public bool $formatOutput ;
readonly public DOMImplementation $implementation ;
public bool $preserveWhiteSpace =true ;
public bool $recover ;
public bool $resolveExternals ;
public bool $standalone ;
public bool $strictErrorChecking =true ;
public bool $substituteEntities ;
public bool $validateOnParse =false ;
public string $version ;
readonly public string $xmlEncoding ;
public bool $xmlStandalone ;
public string $xmlVersion ;
/* Methods */
__construct ([ string $version [, string $encoding ]] )
DOMAttr createAttribute ( string $name )
DOMAttr createAttributeNS ( string $namespaceURI , string $qualifiedName )
DOMCDATASection createCDATASection ( string $data )
DOMComment createComment ( string $data )
DOMDocumentFragment createDocumentFragment ( void )
DOMElement createElement ( string $name [, string $value ] )
DOMElement createElementNS ( string $namespaceURI , string $qualifiedName [, string $value ] )
DOMEntityReference createEntityReference ( string $name )
DOMProcessingInstruction createProcessingInstruction ( string $target [, string $data ] )
DOMText createTextNode ( string $content )
DOMElement getElementById ( string $elementId )
DOMNodeList getElementsByTagName ( string $name )
DOMNodeList getElementsByTagNameNS ( string $namespaceURI , string $localName )
DOMNode importNode ( DOMNode $importedNode [, bool $deep ] )
mixed load ( string $filename [, int $options=0 ] )
bool loadHTML ( string $source )
bool loadHTMLFile ( string $filename )
mixed loadXML ( string $source [, int $options=0 ] )
void normalizeDocument ( void )
bool registerNodeClass ( string $baseclass , string $extendedclass )
bool relaxNGValidate ( string $filename )
bool relaxNGValidateSource ( string $source )
int save ( string $filename [, int $options ] )
string saveHTML ( void )
int saveHTMLFile ( string $filename )
string saveXML ([ DOMNode $node [, int $options ]] )
bool schemaValidate ( string $filename )
bool schemaValidateSource ( string $source )
bool validate ( void )
int xinclude ([ int $options ] )
/* Inherited methods */
DOMNode DOMNode::appendChild ( DOMNode $newnode )
DOMNode DOMNode::cloneNode ([ bool $deep ] )
bool DOMNode::hasAttributes ( void )
bool DOMNode::hasChildNodes ( void )
DOMNode DOMNode::insertBefore ( DOMNode $newnode [, DOMNode $refnode ] )
bool DOMNode::isDefaultNamespace ( string $namespaceURI )
bool DOMNode::isSameNode ( DOMNode $node )
bool DOMNode::isSupported ( string $feature , string $version )
string DOMNode::lookupNamespaceURI ( string $prefix )
string DOMNode::lookupPrefix ( string $namespaceURI )
void DOMNode::normalize ( void )
DOMNode DOMNode::removeChild ( DOMNode $oldnode )
DOMNode DOMNode::replaceChild ( DOMNode $newnode , DOMNode $oldnode )
}
元素节点类DOMElement类型定义如下:
DOMElement extends DOMNode {
/* Properties */
readonly public bool $schemaTypeInfo ;
readonly public string $tagName ;
/* Methods */
__construct ( string $name [, string $value [, string $namespaceURI ]] )
string getAttribute ( string $name )
DOMAttr getAttributeNode ( string $name )
DOMAttr getAttributeNodeNS ( string $namespaceURI , string $localName )
string getAttributeNS ( string $namespaceURI , string $localName )
DOMNodeList getElementsByTagName ( string $name )
DOMNodeList getElementsByTagNameNS ( string $namespaceURI , string $localName )
bool hasAttribute ( string $name )
bool hasAttributeNS ( string $namespaceURI , string $localName )
bool removeAttribute ( string $name )
bool removeAttributeNode ( DOMAttr $oldnode )
bool removeAttributeNS ( string $namespaceURI , string $localName )
DOMAttr setAttribute ( string $name , string $value )
DOMAttr setAttributeNode ( DOMAttr $attr )
DOMAttr setAttributeNodeNS ( DOMAttr $attr )
void setAttributeNS ( string $namespaceURI , string $qualifiedName , string $value )
void setIdAttribute ( string $name , bool $isId )
void setIdAttributeNode ( DOMAttr $attr , bool $isId )
void setIdAttributeNS ( string $namespaceURI , string $localName , bool $isId )
/* Inherited methods */
DOMNode DOMNode::appendChild ( DOMNode $newnode )
DOMNode DOMNode::cloneNode ([ bool $deep ] )
bool DOMNode::hasAttributes ( void )
bool DOMNode::hasChildNodes ( void )
DOMNode DOMNode::insertBefore ( DOMNode $newnode [, DOMNode $refnode ] )
bool DOMNode::isDefaultNamespace ( string $namespaceURI )
bool DOMNode::isSameNode ( DOMNode $node )
bool DOMNode::isSupported ( string $feature , string $version )
string DOMNode::lookupNamespaceURI ( string $prefix )
string DOMNode::lookupPrefix ( string $namespaceURI )
void DOMNode::normalize ( void )
DOMNode DOMNode::removeChild ( DOMNode $oldnode )
DOMNode DOMNode::replaceChild ( DOMNode $newnode , DOMNode $oldnode )
}
文本类型DOMText定义如下:
DOMText extends DOMCharacterData {
/* Properties */
readonly public string $wholeText ;
/* Methods */
__construct ([ string $value ] )
bool isWhitespaceInElementContent ( void )
DOMText splitText ( int $offset )
/* Inherited methods */
void DOMCharacterData::appendData ( string $data )
void DOMCharacterData::deleteData ( int $offset , int $count )
void DOMCharacterData::insertData ( int $offset , string $data )
void DOMCharacterData::replaceData ( int $offset , int $count , string $data )
string DOMCharacterData::substringData ( int $offset , int $count )
}
DOMNode节点定义如下:
DOMNode {
/* Properties */
public readonly string $nodeName ;
public string $nodeValue ;
public readonly int $nodeType ;
public readonly DOMNode $parentNode ;
public readonly DOMNodeList $childNodes ;
public readonly DOMNode $firstChild ;
public readonly DOMNode $lastChild ;
public readonly DOMNode $previousSibling ;
public readonly DOMNode $nextSibling ;
public readonly DOMNamedNodeMap $attributes ;
public readonly DOMDocument $ownerDocument ;
public readonly string $namespaceURI ;
public string $prefix ;
public readonly string $localName ;
public readonly string $baseURI ;
public string $textContent ;
/* Methods */
DOMNode appendChild ( DOMNode $newnode )
DOMNode cloneNode ([ bool $deep ] )
bool hasAttributes ( void )
bool hasChildNodes ( void )
DOMNode insertBefore ( DOMNode $newnode [, DOMNode $refnode ] )
bool isDefaultNamespace ( string $namespaceURI )
bool isSameNode ( DOMNode $node )
bool isSupported ( string $feature , string $version )
string lookupNamespaceURI ( string $prefix )
string lookupPrefix ( string $namespaceURI )
void normalize ( void )
DOMNode removeChild ( DOMNode $oldnode )
DOMNode replaceChild ( DOMNode $newnode , DOMNode $oldnode )
}
3、测试程序
<?php const INDEX_FILE_NAME = "student_file_index.xml"; //文件索引类
class file_index
{
public function set_file_index($file_name, $cur_count, $total_count)
{
$this->file_name = $file_name;
$this->cur_count = $cur_count;
$this->total_count = $total_count;
}
public function get_file_name()
{
return $this->file_name;
}
public function get_cur_count()
{
return $this->cur_count;
}
public function get_total_count()
{
return $this->total_count;
} private $file_name; //文件名
private $cur_count; //当前记录数
private $total_count; //总记录数
} function create_file_index(array $params)
{
$index = new file_index();
$index->set_file_index($params['file_name'],
$params['cur_count'], $params['total_count']);
return $index;
} function create_file_node(DOMDocument $doc, file_index $index)
{
//创建一个file元素
$file = $doc->createElement("file");
//创建一个属性元素
$name_attr = $doc->createAttribute("name");
//将该属性添加到file元素上
$file->appendChild($name_attr); //创建一个文本元素
$file_name = $doc->createTextNode($index->get_file_name());
//将文本元素添加name_attr属性上
$name_attr->appendChild($file_name); //创建一个cur_count元素
$cur_count = $doc->createElement("cur_count", strval($index->get_cur_count()));
//将cur_count添加到file元素下
$cur_count = $file->appendChild($cur_count); //创建一个total_count元素
$total_count = $doc->createElement("total_count",
strval($index->get_total_count()));
//将total_count添加到file元素下
$total_count = $file->appendChild($total_count); return $file;
} function create_index_file($index_file_name, array $params)
{
//创建一个文档
$doc = new DOMDocument("1.0", "utf-8");
//创建根元素
$root = $doc->createElement("index");
$root = $doc->appendChild($root); //创建一个索引结构
$index = create_file_index($params);
$file = create_file_node($doc, $index); //将file看到根元素下
$root->appendChild($file);
$doc->save($index_file_name);
return true;
} function add_index_file($index_file_name, array $params)
{
//创建一个文档
$doc = new DOMDocument();
//加载xml文件
$doc->load($index_file_name);
//获取index元素列表
$node_list = $doc->getElementsByTagName('index');
//获取根元素
$root = $node_list->item(0);
//创建一个索引结构
$index = create_file_index($params);
$file = create_file_node($doc, $index);
//将file看到根元素下
$root->appendChild($file);
$doc->save($index_file_name);
} function traverse_file_index($index_file_name)
{
$file_index = array();
$doc = new DOMDocument();
$doc->load($index_file_name);
//获取file元素集合
$file_list = $doc->getElementsByTagName('file');
//获取cur_count元素集合
$cur_count_list = $doc->getElementsByTagName('cur_count');
//获取total_count元素集合
$total_count_list = $doc->getElementsByTagName('total_count');
for ($i = 0; $i < $file_list->length; $i++) {
$index = new file_index();
//获取file元素的name属性值
$file_name = $file_list->item($i)->attributes->getNamedItem("name")->nodeValue;
$index->set_file_index($file_name, $cur_count_list->item($i)->nodeValue,
$total_count_list->item($i)->nodeValue);
$file_index[$i] = $index;
} return $file_index;
} /*****************for test*********************/
$params = array();
$index_file_name = INDEX_FILE_NAME; if (file_exists($index_file_name)) {
$params['file_name'] = "student_info_2014_02_12";
$params['cur_count'] = 10;
$params['total_count'] = 10;
echo "Add index to file.\n";
add_index_file($index_file_name, $params);
}
else {
$params['file_name'] = "student_info_2014_02_11";
$params['cur_count'] = 23;
$params['total_count'] = 33;
echo "Create index file.\n";
create_index_file($index_file_name, $params);
} //测试读取xm文件
echo "Read index content from ".$index_file_name."\n";
echo "file_name\t\t\tcur_count\ttotal_count.\n";
$file_index = traverse_file_index($index_file_name);
foreach($file_index as $index) {
echo $index->get_file_name();
echo "\t\t ";
echo $index->get_cur_count();
echo strval($cur_count);
echo "\t\t ";
echo $index->get_total_count();
echo "\n";
}
测试结果如下图所示: