转自:http://blog.csdn.net/chowpan/article/details/8645224
1,安装:将GDataXMLNode文件加入至工程中->向Frameworks文件中添加libxml2.dylib库->在Croups & Files 侧边栏中双击工程图标,找到 build 修改两个属性:Search Paths中 找到Header Search Paths 将其对应的值修改为:/usr/include/libxml2,在Linking中找到 Other Linker Flags 对应的值改为:-lxml2。-------安装完成。
2,
//获取工程目录的xml文件
NSString *filePath = [[NSBundlemainBundle] pathForResource:@"users"ofType:@"xml"];
NSData *xmlData = [[NSDataalloc] initWithContentsOfFile:filePath];
//使用NSData对象初始化
NSError *error=nil;
GDataXMLDocument *doc = [[GDataXMLDocumentalloc] initWithData:xmlData options:0 error:&error];
//获取根节点(Users)
GDataXMLElement *rootElement = [doc rootElement];
//获取根节点下的节点(User)
NSArray *users = [rootElement elementsForName:@"User"];
for (GDataXMLElement *userin users) {
//User节点的id属性
NSString *userId = [[user attributeForName:@"id"] stringValue];
NSLog(@"User id is:%@",userId);
//获取name节点的值
GDataXMLElement *nameElement = [[userelementsForName:@"name"] objectAtIndex:0];
NSString *name = [nameElement stringValue];
NSLog(@"User name is:%@",name);
//获取age节点的值
GDataXMLElement *ageElement = [[userelementsForName:@"age"] objectAtIndex:0];
NSString *age = [ageElement stringValue];
NSLog(@"User age is:%@",age);
NSLog(@"-------------------");
}
附:xml文件--
<?xml version="1.0" encoding="utf-8"?>
<Users>
<User id="001">
<name>Ryan</name>
<age>24</age>
</User>
<User id="002">
<name>Tang</name>
<age>23</age>
</User>
</Users>
----------------------------------------------------
GDataXml 相同标签的多个属性
GDataXml 相同标签的多个属性,好多文档都没有介绍获取属性的方法
GDataXMLDocument *doc=[[GDataXMLDocument alloc]initWithXMLString:resp*****eBody opti*****:2 error:nil];
if (doc!=nil) {
GDataXMLElement *root=[doc rootElement ];
NSLog(@"--------root's children:--------\n%@", root);
//取出根节点的所有孩子节点
//取出某一个具体节点(body节点)
[returnInfo setObject:[[[root elementsForName:@"db:uid"] objectAtIndex:0] stringValue] forKey:@"snsUserUid"];
[returnInfo setObject:[[[root elementsForName:@"title"]objectAtIndex:0]stringValue] forKey:@"snsNickName"];
[returnInfo setObject:[[[root elementsForName:@"db:location"]objectAtIndex:0]stringValue] forKey:@"snsProvince"];
[returnInfo setObject:[[[[root elementsForName:@"link"] objectAtIndex:2]attributeForName:@"href"] stringValue] forKey:@"snsProfileImageUrl"];
[returnInfo setObject:@"4" forKey:@"snsLandEntrance"];
NSLog(@"%@",[[[root elementsForName:@"link"] objectAtIndex:2]attributes]);
NSLog(@"%@",[[[root elementsForName:@"db:location"]objectAtIndex:0]stringValue]);
}
NSLog(@"returnInforeturnInforeturnInforeturnInforeturnInfo%@",returnInfo);
附上xml源文件:
<?xml version="1.0" encoding="UTF-8"?>
<entry xmlns="http://www.w3.org/2005/Atom" xmlns:db="http://www.douban.com/xmlns/" xmlns:gd="http://schemas.google.com/g/2005" xmlns:openSearch="http://a9.com/-/spec/opensearchrss/1.0/" xmlns:opensearch="http://a9.com/-/spec/opensearchrss/1.0/">
<id>http://api.douban.com/people/63522291</id>
<title>wangjianlewo</title>
<link href="http://api.douban.com/people/63522291" rel="self"/>
<link href="http://www.douban.com/people/63522291/" rel="alternate"/>
<link href="http://img3.douban.com/icon/user_normal.jpg" rel="icon"/>
<content></content>
<db:attribute name="n_mails">0</db:attribute>
<db:attribute name="n_notificati*****">0</db:attribute>
<db:location id="beijing">北京</db:location>
<db:signature></db:signature>
<db:uid>63522291</db:uid>
<uri>http://api.douban.com/people/63522291</uri>
</entry>
------------------------
下面是得到属性里的值。Google为我们做了很多的事情,不得不感慨GDataXMLNode给我们带来了如此多的便利
直接代码:
NSArray *getItems = [document nodesForXPath:@"//item" error:&error];
这里给出了一个老外写的代码:
/////////////////////// 截取属性应用举例
//NSInteger type=[[(GDataXMLNode *)[[urls objectAtIndex:i] attributeForName:@"type"] stringValue] intValue];
//NSInteger bit_stream=[[(GDataXMLNode *)[[urls objectAtIndex:i] attributeForName:@"bit_stream"] stringValue] intValue];
///////////////////////////////////////////
//// 调试信息 看是否获取属性成功 //////
//////////////////////////////////////////
NSLog(@"%@",[(GDataXMLNode *)[[getItems objectAtIndex:0]attributeForName:@"name"]stringValue] );
//取出document对象
GDataXMLDocument* document = [[GDataXMLDocument alloc] initWithXMLString:myResponseStr options:2 error:nil];
//取出xml的根节点
GDataXMLElement* rootElement = [document rootElement];
NSLog(@"--------root element:--------\n%@",rootElement);
//取出根节点的所有孩子节点
NSArray* children = [rootElement children];
NSLog(@"--------root's children:--------\n%@", children);
//取出某一个具体节点(body节点)
GDataXMLElement* bodyElement = [[rootElement elementsForName:@"item"]objectAtIndex:1];
NSLog(@"--------body:--------\n%@", bodyElement);
//某个具体节点的文本内容
NSString* content = [bodyElement stringValue];
NSLog(@"--------body's content:--------\n%@", content);
//实例
xml的解析在ios网络开发的时候非常常见,不同的xml的树形的结构各不相同,这篇文中介绍根据不同的xml的结构解析出xml,保存到字典中,如果解析的数据将会多次用到,建议建立数据实体,不然在多个场景中都必须知道字典中的键值,用起来非常不方便。
我最近开发的项目中用到xml解析,我用到一个工厂模式来建立一个解析的方式。
1: 我在这个过程中用到6个文件,BaseParser.h,BaseParser.m,DataParser.h和DataParser.m ,LoginParser.h,LoginParser.m,其中BaseParser用于定义和实现基类的方法,LoginParser继承于BaserParser,实现了父类中申明的解析xml文件和组装xml文件的方法。DataParser中根据不同的xml类型来实例化解析类,这里就是LoginParser(也就是说,还可以实例化任意多个BaseParser的子类).
2,GDataxmlNode 的使用在LoginParser中很能得以体现总的思路就是 字典,字符串,GDataxmlDocumet 这个类型的实例之间相互转化,以完成xml的组装和解析。
BaseParser.h
- #import <Foundation/Foundation.h>
- #import "GDataXMLNode.h"
-
- @interface BaseParser : NSObject
- {
- NSString *xmlContent; //字符串形式的xml内容
- NSMutableDictionary *parsedContent; //对应的字典
- }
-
- @property(nonatomic,retain)NSString *xmlContent;
-
- - (id)initWithXmlString:(NSString *)xmlString;
- - (NSDictionary *)getCurrentList;
- - (id)initWithUserDicionary:(NSDictionary*)dicionary;
- - (id)getCurrentData;
- @end
BaseParser.m
- #import "BaseParser.h"
- @implementation Baseparser
- @synthesize xmlContent;
- -(id)init
- {
- self = [super init];
- if (self) {
- parsedContent = [[NSMutableDictionary alloc]init];
- xmlContent = [[NSString alloc]init];
- }
- return self;
- }
- -(void)dealloc
- {
- [parsedContent release];
- [xmlContent release];
- [super dealloc];
-
- }
- - (id)initWithXmlString:(NSString *)xmlString
- {
- return nil;
- }
- - (id)initWithUserDicionary:(NSDictionary *)dicionary
- {
- return nil;
- }
-
- - (NSDictionary *)getCurrentList
- {
- return [NSDictionary dictionaryWithDictionary:parsedContent];
- }
- - (id)getCurrentData
- {
- return [NSString stringWithString:xmlContent];
- }
LoginParser.h
- #import <Foundation/Foundation.h>
- #import "BaseParser.h"
-
- @interface LoginParser : BaseParser
-
- @end
LoginParser.m
- #import "LoginParser.h"
-
- @implementation LoginParser
- - (void)dealloc
- {
- [super dealloc];
- }
- - (id)initWithXmlString:(NSString *)xmlString
- {
- self = [super init];
- if (self) {
- NSError *error;
- GDataXMLDocument *dataDocument = [[GDataXMLDocument alloc]initWithXMLString:xmlString options:0 error:&error ];
- GDataXMLElement *root = [dataDocument rootElement];
- NSArray *array = [NSArray arrayWithObjects:@"code",@"desc",@"sessionId",@"user_id",@"name", nil];
- for (int index = 0; index<[array count]; index++) {
- GDataXMLElement *element = [[root elementsForName:[array objectAtIndex:index]]lastObject];
- NSString *aValue = (NSString*)[element stringValue];
- if (aValue) {
- [parsedContent setObject:aValue forKey:[array objectAtIndex:index]];
- }
- }
- [dataDocument release];
-
- }
- return self;
- }
- - (id)initWithUserDicionary:(NSDictionary *)dicionary
- {
- self = [self init];
- if (self) {
- [dicionary retain];
- GDataXMLElement *rootElement = [GDataXMLElement elementWithName:@"root"];
- NSArray *elementArray = [NSArray arrayWithObjects:@"name",@"type",@"password", nil];
- for (int index = 0; index<[elementArray count]; index++) {
- GDataXMLElement *element = [GDataXMLElement elementWithName:[elementArray objectAtIndex:index] stringValue:[dicionary objectForKey:[elementArray objectAtIndex:index]]];
- [rootElement addChild:element];
- }
- [dicionary release];
- GDataXMLDocument *xmlDocument = [[GDataXMLDocument alloc]initWithRootElement:rootElement];
- NSString *xmlString = [[NSString alloc]initWithData:xmlDocument.XMLData encoding:NSUTF8StringEncoding];
- xmlContent = @"";
- xmlContent = [xmlContent stringByAppendingString:xmlString];
- [xmlString release];
- [xmlDocument release];
-
- }
-
- return self;
- }
DataParser.h
- #import <Foundation/Foundation.h>
-
- @interface DataParser : NSObject
-
-
- + (id)CreateParserObjectWithData:(id)xmlString andTypeIs:(NSInteger)aType; // 根据不同的类型用字典组装成xml
- + (id)CreateDeparserObjectWithData:(id)xmlString andTypeIs:(NSInteger)aType;//将xml解析成字典
- @end
DataParser.m
- #import "LoginParser.h"
- @implementation DataParser
- //这俩个简单的工厂来组装和解析xml
- + (id)CreateParserObjectWithData:(id)xmlString andTypeIs:(NSInteger)aType
- {
- switch (aType) {
- case LOGINSERVICETYPE :
- {
- LoginParser *parser = [[BCLogin alloc]initWithXmlString:xmlString];
- NSDictionary *dictionary = [urlList getCurrentList];
- [ parser release];
- return dictionary ;
- }
- break;
- }
- + (id)CreateDeparserObjectWithData:(id)xmlString andTypeIs:(NSInteger)aType
- {
-
- switch (aType) {
- case LOGINSERVICETYPE :
- {
- LoginParser *parser = [[BCLogin alloc]initWithUserDicionary:xmlString];
- NSData *data = [urlList getCurrentData];
- [parser release];
- return data ;
- }
- break;
- }
4:使用
新建一个文件LoginViewController,在程序束中加入 LoginReturn.xml,
LoginViewController.m
- #define LOGINSERVICETYPE 100
- #import "LoginViewController.h"
-
- @implementation LoginViewController
-
- - (id)initWithNibName:(NSString *)nibNameOrNil bundle:(NSBundle *)nibBundleOrNil
- {
- self = [super initWithNibName:nibNameOrNil bundle:nibBundleOrNil];
- if (self) {
- // Custom initialization
- }
- return self;
- }
-
- - (void)didReceiveMemoryWarning
- {
- // Releases the view if it doesn't have a superview.
- [super didReceiveMemoryWarning];
-
- // Release any cached data, images, etc that aren't in use.
- }
-
- #pragma mark - View lifecycle
-
- - (void)viewDidLoad
- {
- [super viewDidLoad];
- // Do any additional setup after loading the view from its nib.
- <span style="color:#FF0000;"> //使用解析的工厂,组装xml就不写了
- NSString *string = NSError *error;
- NSString *xmlString = [NSString stringWithContentsOfFile:[[[NSBundle mainBundle]bundlePath]stringByAppendingPathComponent:@"LoginReturn.xml"]
- encoding:NSUTF8StringEncoding error:&error];
- NSMutableDictionary *dic = [NSMutableDictionary dictionaryWithDictionary:
- [BCBaseParser CreateParserObjectWithData:xmlString andTypeIs:self.parserType]]
- //这里获得的dic就是包含了sessionId,userId,等键的字典</span>
- }
-
- - (void)viewDidUnload
- {
- [super viewDidUnload];
- // Release any retained subviews of the main view.
- // e.g. self.myOutlet = nil;
- }
-
- - (BOOL)shouldAutorotateToInterfaceOrientation:(UIInterfaceOrientation)interfaceOrientation
- {
- // Return YES for supported orientations
- return (interfaceOrientation == UIInterfaceOrientationPortrait);
- }
-
- @end
不好把我在项目中的代码貼出来,我是在post不同的xml中用到这个方式
转载请注明出处
总结:
代码的重用非常重要,在开发过程中尽量遵守一般的开发原则,比如OCP,这篇文中较好的体现了这一原则,同时GDataXmlNode避免了官方的类回调的使用,十分方便,推荐使用。