----------------------------------------------------------------------------------------------------------------
expat是使用C所写的XML解释器,采用流的方式来解析XML文件,并且基于事件通知型来调用分析到的数据,并不需要把所有XML文件全部加载到内存里,这样可以分析非常大的XML文件。由于 expat库是由XML的主要负责人James Clark来实现的,因此它是符合W3C的XML标准的。
---------------------------以上为转载-------------------------------------
正因为源码全部是纯C所写,因此,非常容易移植,尤其是适用于嵌入式平台,我在往联芯的手机平台上移植时,几乎没改任何东西。
不过,优点也带来了缺点,因为是采用流的方式解析XML,所以不会像TinyXML那样在一块内存中生成基于DOM的树。
虽然这样解析起来略显麻烦,但是基于回调的机制,在我看来还是蛮方便的。
下面就说使用方法:
首先是用XML_ParserCreate(const XML_Char *encodingName),参数一般为NULL,函数返回一个XML_Parser类型指针,我们就当他是一个句柄吧,类似于Windows里的内核对象,一般需要保存在一个全局的指针里。
然后调用XML_SetElementHandler(XML_Parser parser,
XML_StartElementHandler start,
XML_EndElementHandler end)
第一个参数是那个Parser句柄,第二个和第三个参数则是整个Parser的核心,类型为CallBack的函数,不了解CallBack函数的,我在这里简单说下,函数调用一般分为两种,一种是主调,即编写代码者,自己调用的函数,还一种成为Callback函数,编码者写好,但他自己却不主动调用,而是在某些条件下(编码者并不清楚具体时间和流程),由其他函数调用,比如简单的,如设备驱动,操作系统提供了一组某个设备的函数指针,比如LCD屏驱动,由一组画点,画线,画块等函数组成,当更换LCD时,只需要把操作系统开放的函数指针,指向你提供的接口即可,操作系统再需要时,会自动调用你的驱动函数,这就是回调函数一个典型的例子。
这二个回调分别是对应于解析<>和</>, 下面分别详细介绍这个2个回调函数。
typedef void (XMLCALL *XML_StartElementHandler) (void *userData,
const XML_Char *name,
const XML_Char **atts);
其中第一个参数userData, 可以由函数XML_SetUserData(XML_Parser parser, void *p)设置,参数就不用说了吧?
后面两个参数,我用个具体的列子说明下,这样更好理解:
比如有个标准XML,某个标签属性如下:
<feed version="2.0" ctxt-id="9212" template-id="default" feed-type="ftti">
那么StartElementHandler回调返回的name就是标签"feed", **atts是一个指针数组,分别指向标签的一组属性,atts[0]就是"version", atts[1]就是"2.0", 以此类推。应该很清楚了吧?呵呵。
这时候必然有个对应的</feed>,
typedef void (XMLCALL *XML_EndElementHandler) (void *userData,
const XML_Char *name);
就是处理标签结束的,name就是"feed”了,这个回调一般是用户设置自己的状态机的。
最后一个函数就是XML_SetCharacterDataHandler(XML_Parser parser,XML_CharacterDataHandler handler)
这个函数是设置处理一个<>和</>之间的字段的回调。
回调原型如下:
typedef void (XMLCALL *XML_CharacterDataHandler) (void *userData,
const XML_Char *s,
int len);
其中第二个参数是一块Buffer的指针,如果你单步DEBUG后,你会发现expat用的就是你传入的那块Buffer(这块Buffer下面讲解),比如:
<title>天气</title>
<summary>28日08时至29日08时,陕西中南部、山西西南部、河南中南部、湖北北部、四川中东部、重庆西部和北部、贵州西部等地的部分地区有大雨或暴雨,河南南部、湖北北部等地局部有大暴雨。【点击“更多”查询其他城市天气】</summary>
假设目前解析到天气这个charData, 如果你看那个指针的所有内容的话,实际上是这样的:
天气</title>
<summary>28日08时至29日08时,陕西中南部、山西西南部、河南中南部、湖北北部、四川中东部、重庆西部和北部、贵州西部等地的部分地区有大雨或暴雨,河南南部、湖北北部等地局部有大暴雨。【点击“更多”查询其他城市天气】</summary>
所有要根据第三个参数len来确定正确的数据。
但这里有个非常隐晦的问题,如果不知道的话,会带来很大麻烦,下面说。
最后就是parse,调用
XML_Parse(XML_Parser parser, const char *s, int len, int isFinal)
第二个参数是用户指定的Buffer指针, 第三个是这块Buffer中实际内容的字节数,最后参数代表是否这块Buffer已经结束。比如要解析的XML文件太大,但内存比较吃紧,Buffer比较小,则可以循环读取文件,然后丢给Parser, 在文件读取结束前,isFinal参数为FALSE,反之为TRUE。
这里的Buffer如果太小则会造成上面提到那个隐晦的问题,
XML_CharacterDataHandler一次返回的可能并不是完整的CharData,比如这个charData的Len大于你的 Buffer大小,那这是会连续调用2次XML_CharacterDataHandler,我们需要将2次结果拼接起来,以得到正确结果,因此我们的状态机一定要考虑到这点。
顺便说下XML_ParserReset(XML_Parser parser, const XML_Char *encodingName)函数,在某些时候,如果你不确定前后2次XML是否一样的情况下,比如网络上投递的XML,在一次解析后最好调用一次本函数,否则会出现意料之外的结果。比如前后两次XML完全一样,可这你并不知情,那么XML_Parse()会返回失败。
分享到:
相关推荐
Expat是一个用C语言编写的XML解析库,最初是作为开源项目,归属于Mozilla项目的一部分。它由著名的XML专家James Clark创建,他也是groff、Jade、XP(一个Java XML解析器包)、XT(一个Java XSL引擎)等众多工具包的...
Expat 是一个开源的 XML 解析器,由 C 语言编写,最初是 Mozilla 项目的一部分。它的主要开发者是 James Clark,他还开发了其他知名的软件工具,如 groff、Jade、XP(Java XML 解析器包)和 XT(Java XSL 引擎)。...
在实际使用中,开发者首先需要包含`ExpatImpl.h`,然后创建`XMLParser`对象,设置必要的回调函数,最后调用解析方法开始解析XML。通过这种方式,C++开发者可以利用Expat的强大解析能力,同时享受到C++语言的面向对象...
`node-expat`就是这样一款专为Node.js设计的开源库,它提供了快速、高效的XML解析能力。 `node-expat`是基于libexpat,一个C语言编写的轻量级XML解析库,将其通过Node.js的C++扩展接口进行封装,使得开发者可以在...
**GSA Simple XML Parser** 是一个基于PHP的开源XML解析器,它采用了DOM(Document Object Model)风格的设计,使得开发者能够方便地处理XML文档。在理解这个解析器之前,我们首先需要了解XML(eXtensible Markup ...
Expat 是一个开源的、轻量级的XML解析库,主要设计用于小型系统和嵌入式环境。在本文中,我们将深入探讨Expat XML解析库的原理、功能、使用方法以及其在项目中的应用。 首先,Expat 提供了一个C语言实现的API,允许...
请注意,我们正在迁移到GitHub:https://github.com/libexpat/libexpat这是James Clark的C语言中的Expat XML解析器库。它是一个面向流的解析器,需要设置处理程序来处理结构。解析器在文档中发现的。 请注意,我们...
Expat 是一个开源库,主要用于解析XML(可扩展标记语言)文档。它的全名是 "External Entity Processor and Parser",由 James Clark 开发,并在1998年首次发布。这个库是用C语言编写的,因此可以在多种操作系统上...
标题中的"SAXY"是一个基于PHP的开源XML解析器,其设计灵感来源于Expat解析器。这个解析器采用SAX(Simple API for XML)模式,它不同于DOM解析器,SAX解析器不是将整个XML文档加载到内存中,而是逐行进行事件驱动的...
XML_Parser是Expat库的一个实现,由James Clark开发,是一个高效的、非验证的XML解析器,它不支持XML的命名空间特性。C++Binding则是在C++环境中封装了这个解析器,提供了面向对象的API,使得C++开发者可以更方便地...
Expat,全称XML Expat Parser,是由James Clark开发的C语言实现的轻量级XML解析器,它不提供完整的DOM(Document Object Model)模型,但支持SAX(Simple API for XML)事件驱动的解析方式。 **SAX与DOM解析方式** ...
Expat是一个用C语言开发的、用来解析XML文档的开发库,它最初是开源的、Mozilla 项目下的一个XML解析器。这个库的开发者是James Clark, 还开发了很多我们所熟知的工具包:groff、 Jade、 XP (a Java XML parser ...
eXML 是 Eiffel 的 XML 解析器框架。 它具有本机 Eiffel 解析器和 expat(使用 C 桥)。 请注意,我们使用的是 http://www.egroups.com/group/exml 上的邮件列表(而不是 SF 上的邮件列表)
3. **XML解析库**:CEGUI使用XML来定义界面布局和外观,其中主要使用了ExpatParser来解析XML文件。其他可能的解析库包括TinyXML或pugixml,但CEGUI项目通常只包含ExpatParser。 4. **图像解码库**:所有带有"codec...
libexpat是一个开源的XML解析库,它的全称为"Expat XML Parser",在各种操作系统平台上广泛使用,包括但不限于Linux。该库的核心功能是解析XML文档,将XML数据结构化为程序可以处理的形式。libexpat-R_2_4_1.zip是一...
VS2019 x64 Release环境编译好的libkml库是一套...通过更新的第三方库,如expat和uriparser,它能提供更加稳定和高效的服务。开发者在使用时,应充分了解KML标准和libkml的API,以便更好地利用这个库来实现其项目需求。
Expat库,全称为“XML Parser Library written in C”,是一个小型且高效的XML解析器,它不支持XML的DOM(文档对象模型)或SAX(简单API for XML),而是采用事件驱动的方式处理XML文档。这种设计使得Expat在内存...
SwiftyExpat 是简单的 Expat XML Parser 的封装,可以使用块,而不用函数指针调用。 SwiftyExpat 包括两个部分: SwiftyExpat SwiftyExpatTests SwiftyExpat let p = Expat() .onStartElement { name, ...
源码包包含了第三方库如`expat`和`uriparser`,它们是编译和运行libkml所必需的依赖。 `expat`是一个轻量级的XML解析库,用于读取和写入XML文档。在libkml中,它被用来解析和生成KML文件中的XML结构,确保数据的...