tinyxml2之解析xml文件

 tinyxml2是什麼?

 tinyXML2是一個開源的解析XML的C++庫,用於c++項目裏面解析xml文件使用。

下載地址:

https://github.com/leethomason/tinyxml2 ,使用git直接將源碼下載下來。

使用方法:

將下載的源碼包裏面的tinyxml2.h,tinyxml2.cpp拷貝到自己的項目, 使用時包含頭文件,並且

使用編譯指令:using namespace tinyxml2 ,編譯的時候記得加上tinyxml2.cpp,

使用:

#include"tinyxml2.h"

using namespace tinyxml2;

編譯:g++  main.cpp tinyxml2.cpp -o a.out 

tinyxml2常用類介紹:

結構圖:


XMLNode所有DOM模型節點類的父類,基本節點類;

XMLDocument:文檔類,它表示整個xml文件對象;

XMLElement元素類,它是文件的主要部分,支持嵌套,可以包含屬性類和文本類等,是使用最多的類。

XMLText文本元素類,如:<name>i am student</name>,name節點的i am student就是文本元素。

XMLAttribute元素屬性類,節點的所有屬性。不是XMLNode的子類;

XMLDeclaration聲明類,xml文件第一行的內容,聲明xml版本,和所用的編碼集,很少用到,

如: <?xml version="1.0" standalone="yes"?>

XMLComment註釋節點類,註釋部分,一般都不會使用這個類。

XMLUnknown未識別的節點類

用的最多的就是紅色標記的2個類。

XMLElement常用方法:

下面四個都可以帶參數來限制查找,不帶參數默認第一個;

XMLElement* FirstChildElement( const char* name = 0):獲取第一子節點,此節點裏麪包含的第一個節點

XMLElement* LastChildElement( const char* name = 0):獲取最後一個節點

XMLElement* NextSiblingElement( const char* name = 0):獲取下一個兄弟節點,同級別的節點

XMLElement*PreviousSiblingElement( const char* name = 0):獲取上一個兄弟節點


const XMLAttribute* FirstAttribute(void):獲取節點的第一個屬性,返回的是const類型的。

char *Attribute( const char* name, const char* value=0 ):根據屬性名稱,獲取屬性值,返回char*類型的屬性值

XMLNode*Parent(void):獲取父節點返回的是XMLNode*類型的,可以轉換對應的類型xxx.Parent()->ToElement()->Name();

const char*  GetText():獲取文本元素

XMLAttribute類常用方法:

const char* Name();獲取屬性名稱

const char* Value();獲取屬性值

const XMLAttribute* Next();獲取下一個屬性

其實掌握了上面常用的方法,使用tinyxml2就很簡單了。

#include<stdio.h>
#include<string>
#include<iostream>
#include "tinyxml2.h"  //引用頭文件
using namespace std;
using namespace tinyxml2; //使用名稱空間
void show_all_node(XMLElement *tmpnode)
{
	while(tmpnode)
	{
		cout<<"<"<<tmpnode->Name()<<">";
		//獲取節點屬性第一個
		const 	XMLAttribute* tmp_attr = tmpnode->FirstAttribute();
		//遍歷整個屬性列表
		while(tmp_attr)
		{
			cout<<"attr="<<tmp_attr->Name()<<":"<<tmp_attr->Value()<<",";
			//獲取下一個屬性節點
			tmp_attr=tmp_attr->Next();
		}
		if(tmpnode->GetText())//一定要判斷不然會有問題,如果文本爲空的話,會打印text=後直接結束進程
			cout<<" text="<<tmpnode->GetText()<<";"<<endl;
		show_all_node(tmpnode->FirstChildElement());//遞歸掉用,打印子節點所有屬性和文本信息
		//獲取同級別的下一個兄弟元素
		tmpnode=tmpnode->NextSiblingElement();
	}
}


int main()
{
	XMLDocument doc;
	doc.LoadFile("./dream.xml");//第一步加載文檔

	XMLElement*root=doc.RootElement();//獲取根元素,通過XMLDocument來獲取
	cout<<root->Name()<<endl;
        XMLDeclaration *decl;//獲取聲明不能直接doc->ToDeclaration();
     //不能使用doc.FirstChildElement()->ToDeclaration();
     decl=doc.FirstChild()->ToDeclaration();
     if(decl!=NULL)
     {
	 cout<<	 decl->Value()<<endl;
     }
	
        //show_all_node(root);//遍歷root節點下的所有節點
	//獲取第一個節點
	XMLElement*tmpnode=root->FirstChildElement();
	cout<<tmpnode->Name()<<endl;//打印名稱

	tmpnode=tmpnode->LastChildElement("LINE");//獲取最後一個名稱爲LINE的元素
	cout<<tmpnode->Name()<<endl;//打印名稱

	tmpnode=tmpnode->PreviousSiblingElement("SPEAKER");//獲取前一個名稱爲SPEAKER的元素
	//獲取元素文檔內容
	if(tmpnode->GetText())//這裏要加個判斷,不加如果爲空的化,下面打印會出問題,目前不知到原因。
	{
		cout<<tmpnode->GetText()<<endl;
	}

   const XMLAttribute*attr=tmpnode->FirstAttribute();//獲取元素第一個屬性節點,注意返回的是const類型的
   cout<<attr->Name()<<":"<<attr->Value()<<endl;//打印屬性名稱和值
     
   const XMLAttribute*attr2=attr->Next();//獲取下一個屬性
   cout<<attr->Name()<<":"<<attr->Value()<<endl;//打印屬性名稱和值
   
   cout<<tmpnode->Attribute("name")<<endl;//直接獲取name元素屬性值

    // doc.Print();//打印整個文檔內容
    return 0;
}


dream.xml文件內容,

<?xml version="1.0"?>
<!-- 註釋節點-->

<PLAY>

<SPEECH>
<SPEAKER  id="1" name="speakattr">text node</SPEAKER>
<LINE>What, dead, my dove?</LINE>
<LINE>Speak, speak. Quite dumb?</LINE>
</SPEECH>

<SPEECH2>
<SPEAKER id="2" name="speaker2">PUCK</SPEAKER>
<LINE>So, good night unto you all.</LINE>
</SPEECH2>

</PLAY>

liunx環境編譯:g++ main.cpp tinyxml2.cpp  -o tinytest

./tinytest

PLAY
xml version="1.0"
SPEECH
LINE
text node
id:1
id:1
speakattr

可以去掉遍歷節點函數註釋:show_all_node(root);

函數打印如下:

./tinytest 
PLAY
xml version="1.0"
<PLAY><SPEECH><SPEAKER>attr=id:1,attr=name:speakattr, text=text node;
<LINE> text=What, dead, my dove?;
<LINE> text=Speak, speak. Quite dumb?;
<SPEECH2><SPEAKER>attr=id:2,attr=name:speaker2, text=PUCK;
<LINE> text=So, good night unto you all.;

SPEECH
LINE
text node
id:1
id:1
speakatt

注意事項:tmpnode->GetText()不進行是否爲空判斷會有問題,如果文本爲空的話,會打印text=後直接結束進程。






發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章