TinyXML-2解析XML数据

原创 2015年11月18日 19:55:22

声明

本文例子源自在C++中使用TinyXML2解析xml一文,其余部分来源于网络搜集,难免疏漏,敬请随意吐槽。

XML以及JSON

什么是XML

XML
根据Wikipedia-XML的说法:

可扩展标记语言(英语:eXtensible Markup Language,简称:XML),是一种标记语言。标记指计算机所能理解的信息符号,通过此种标记,计算机之间可以处理包含各种信息的文章等。如何定义这些标记,既可以选择国际通用的标记语言,比如HTML,也可以使用像XML这样由相关人士自由决定的标记语言,这就是语言的可扩展性。XML是从标准通用标记语言(SGML)中简化修改出来的。它主要用到的有可扩展标记语言、可扩展样式语言(XSL)、XBRL和XPath等。
XML设计用来传送及携带数据信息,不用来表现或展示数据,所以XML用途的焦点是它说明数据是什么,以及携带数据信息。

我个人对XML了解不多,这次使用也是用来保存机器学习生成的模型,感觉上用XML来传输存储信息是很方便的。

XML和JSON

JSON是另一种可以用来传输货保存信息的格式。根据Wikipedia-JSON的说法:

JSON(JavaScript Object Notation)是一种由道格拉斯·克罗克福特构想设计、轻量级的资料交换语言,以文字为基础,且易于让人阅读。尽管JSON是Javascript的一个子集,但JSON是独立于语言的文本格式,并且采用了类似于C语言家族的一些习惯。

关于XML和JSON的比较,Wikipedia上如是说:

JSON与XML最大的不同在于XML是一个完整的标记语言,而JSON不是。这使得XML在程式判读上需要比较多的功夫。主要的原因在于XML的设计理念与JSON不同。XML利用标记语言的特性提供了绝佳的延展性(如XPath),在数据存储,扩展及高级检索方面具备对JSON的优势,而JSON则由于比XML更加小巧,以及浏览器的内建快速解析支持,使得其更适用于网络数据传输领域。

关于这一问题,在国内的知乎上也有各种讨论,比如:《为什么XML这么笨重的数据结构仍在广泛应用》《为什么都反对 XML 而支持使用 JSON》。总结下来,基本也就是各有优势,具体选择还是需要根据需要判断。

XML解析库

各种语言都有XML的解析方案,Java和Python都有方便的解析库。对于C++也有多种解析方案,可以参考《C++解析xml有什么好用的轮子》《What XML parser should I use in C++?》。也有人做了一张图:

CXML

我最终选择了TinyXML2,使用挺方便简单。

话说Json似乎有个RapidJSON很好用(传说、传说而已),有空可以尝试一下。

TinyXML2

配置TinyXML2

TinyXML是一个C++的开源解析XML的解析库,根据TinyXML下载页面的介绍:

TinyXML is a simple, small, minimal, C++ XML parser that can be easily integrating into other programs. It reads XML and creates C++ objects representing the XML document. The objects can be manipulated, changed, and saved again as XML.

TinyXML已经停止开发了,现在推荐使用后续版本TinyXML2。

XinyXML2的文档:TinyXML2 Documentation
下载页面在GitHub上:leethomason/tinyxml2

使用的时候只需把项目下载下来,解压,把tinyxml2.h和tinyxml2.cpp拷到工程目录里。使用的时候加入#include"tinyxml2.h"即可。

TinyXML2使用

TinyXML2的使用可以参考TinyXML2 Documentation以及在C++中使用TinyXML2解析xml

TinyXML读取文件

使用TinyXML2读取文件可以使用:

XMLDocument doc;
doc.LoadFile( "resources/dream.xml" );

TinyXML解析XML字符串

使用TinyXML2解析内存中XML字符串可以使用:

static const char* xml = "<element/>"; //XML字符串
XMLDocument doc;
doc.Parse( xml );//解析XML字符串

TinyXML解析XML数据

在从文件或者字符串中取得XML数据之后,可以使用TinyXML2进行解析。

首先说明几个我用到的函数:

//获取DOM的根元素,等同于FirstChildElement()
XMLElement* tinyxml2::XMLDocument::RootElement()

//取得第一个子元素(使用默认参数),或者根据const char * value的值获取第一个name等同value的子元素
const XMLElement* tinyxml2::XMLNode::FirstChildElement( const char * value = 0 ) const

//返回第一个子结点,如果不存在则返回null
const XMLNode *FirstChild () const

//根据valude返回当前node的下一名为valude的元素
const XMLElement * NextSiblingElement (const char *value=0) const

//返回列表中下一属性
const XMLAttribute * Next () const

//返回属性的名字,如<scene name="Depth">中name="Depth"为属性,其名字为name
const char * Name () const

//返回列表第一个属性值如<scene name="Depth">中name="Depth"为属性,其值为Depth
const XMLAttribute *FirstAttribute () const

//方便的访问元素内容的函数,如元素为<foo>This is text</foo>,则返回指向字符串"This is text"的指针。
const char* tinyxml2::XMLElement::GetText() const

具体例子参考在C++中使用TinyXML2解析xml,假设XML内容如下:

<?xml version="1.0"?>  
<scene name="Depth">  
    <node type="camera">  
        <eye>0 10 10</eye>  
        <front>0 0 -1</front>  
        <refUp>0 1 0</refUp>  
        <fov>90</fov>  
    </node>  
    <node type="Sphere">  
        <center>0 10 -10</center>  
        <radius>10</radius>  
    </node>  
    <node type="Plane">  
        <direction>0 10 -10</direction>  
        <distance>10</distance>  
    </node>  
</scene>  

对其进行测试代码为

#include <iostream>
#include <string> 

#include"tinyxml2.h" 

using namespace std;

int main()  
{  
    tinyxml2::XMLDocument doc;  
    doc.LoadFile("test.xml");  

    tinyxml2::XMLElement *scene=doc.RootElement();   
    tinyxml2::XMLElement *surface=scene->FirstChildElement("node");  
    while (surface)  
    {  
        tinyxml2::XMLElement *surfaceChild=surface->FirstChildElement();  
        const char* content;  
        const tinyxml2::XMLAttribute *attributeOfSurface = surface->FirstAttribute();  
        cout<< attributeOfSurface->Name() << ":" << attributeOfSurface->Value() << endl;  
        while(surfaceChild)  
        {  
            content=surfaceChild->GetText();  
            surfaceChild=surfaceChild->NextSiblingElement();  
            cout<<content<<endl;  
        }  
        surface=surface->NextSiblingElement();  
    }   
    return 0;  
}  

输出结果为:

Result

需要注意的是:
GetText()的使用仅限于<foo>This is text</foo>类型元素。对于<foo><b>This is text</b></foo>类型结果会null,<foo>This is <b>text</b></foo>类型结果为”This is “。更为安全的访问元素的方法是使用形如一下的方法:

XMLText* textNode = titleElement->FirstChild()->ToText();
title = textNode->Value();
printf( "Name of play (2): %s\n", title );

总结

以上就是一些TinyXML-2解析XML数据的简单介绍,之前想写的很多,写上才发现很多东西因为理解不够所以表述不清,只希望在作为自己的记录的同时,能够给刚刚接触TinyXML2的人一些简单的介绍,如有更多需求请参考官方文档。

Reference

版权声明:本文为博主原创文章,未经博主允许不得转载。

相关文章推荐

在C++中使用TinyXML2解析xml

读取和设置xml配置文件是最常用的操作,试用了几个C++的XML解析器,个人感觉TinyXML是使用起来最舒服的,因为它的API接口和Java的十分类似,面向对象性很好。       TinyXML...
  • educast
  • educast
  • 2013年10月21日 12:37
  • 23396

TinyXML2使用教程

TinyXML2是simple、small、efficient开源的C++ XML文件解析库,可以很方便的应用到现有的项目之中。非常适合存储简单数据,配置文件,对象序列化等数据量不是很大的操作。Tin...

使用tinyxml2库解析xml

tinyxml2简介tinyxml2是c++编写的轻量级的xml解析器,而且是开放源代码的,在一些开源的游戏引擎中用的比较多。源码托管在github上。 源码地址:https://github.co...

tinyxml2的简单运用

tinyxml2简介: tinyxml2是一个c++xml解析器,它非常高效,而且非常的小,可以很好地嵌入到其他的程序,几乎可以在所有场景运用(我的经验来看) tinyxml2简单读取...

tinyxml2读写XML文件的例程

例程很简单,因此就不再啰嗦了,直接上代码。 test.xml内容: 0 10 10 0 0 -1 0 1 0 90 0 10 -10 10 ...
  • zhawk
  • zhawk
  • 2017年03月08日 19:43
  • 923

TinyXML2读取和创建XML文件

TinyXML2是simple、small、efficient C++ XML文件解析库!方便易于使用,是对TinyXML的升级改写!源码见本人上传到CSDN的TinyXML2.rar资源,或者到官网...

在C++中使用TinyXML2解析xml

读取和设置xml配置文件是最常用的操作,试用了几个C++的XML解析器,个人感觉TinyXML是使用起来最舒服的,因为它的API接口和Java的十分类似,面向对象性很好。       TinyXML...

cocos2dx tinyxml读写示例,tinyxml2读xml示例,

#include #include #include "cocos2d.h" #include "../support/tinyxml2/tinyxml2.h" #include "../Too...

使用tinyxml2生成和解析xml文档

xml文档主要用于储存数据进行配置。 tinyxml2的官方文档 https://github.com/leethomason/tinyxml2 第一步是建立一个c++文件 这里使用的是qt cre...
  • WAN_EXE
  • WAN_EXE
  • 2017年04月13日 11:55
  • 655

TinyXML2 学习

换cocos2d-x版本到2.1.3之后,自己的文件读写也用了引擎CCUserDefault使用的TinyXML2,在这汇总了一下TinyXML2的使用,希望大家看这一篇文章就可以解决自己的问题,省得...
内容举报
返回顶部
收藏助手
不良信息举报
您举报文章:TinyXML-2解析XML数据
举报原因:
原因补充:

(最多只允许输入30个字)