时间:2017年06月02日星期五
说明:本文部分内容均来自慕课网。@慕课网:http://www.imooc.com
教学示例源码:无
个人学习源码:https://github.com/zccodere/s...

第一章:课程介绍

1-1 课程介绍

数据解析使用场景

配置文件与应用系统
客户端与服务端

示意图

clipboard.png

clipboard.png

两种数据格式

JSON
XML

JSON数据格式

clipboard.png

常见JSON库

TouchJson
JSONKit
JASN库
SBJson
苹果JSON库【推荐使用】

XML数据格式

clipboard.png

常见XML库

SAX
DOM

第二章:JSON简介和数据解析

2-1 JSON介绍

什么是JSON

JSON:JavaScript Object Notation

JSON基本组织形式

clipboard.png
JSON本质

clipboard.png

JSON语义分析

clipboard.png

示例:组织信息为JSON

clipboard.png

JSON库

原生JSON解析库:iOS5+【推荐使用】
TouchJson
SBJson
JSONKit

JSON库与APP的关系

clipboard.png

2-2 JSON解析案例一

代码演示:

/*
 iOS5+自带JSON操作库
 
 数据解析:
    要求:分别解析以下JSON数据
        {"name":"James","age":"30"}
        {"user":{"name":"James","age":"30"}}
        [{"name":"James"},{"name":"jim"}]
        {"user":[{"name":"James"},{"name":"jim"}]}
    目的:掌握通过NSJSONSerialization类解析JSON数据
    重点:掌握静态函数JSONObjectWithData:options:error:的使用
 */
// 解析JSON数据从字符串
- (void)jsonOnStr{
    _tvParseResult.text = [_tvParseResult.text stringByAppendingString: @"\n"];
    
    //NSString *jsonStr = @"{\"name\":\"James\",\"age\":\"30\"}";
    //NSString *jsonTreeStr = @"{\"user\":{\"name\":\"James\",\"age\":\"30\"}}";
    //NSString *jsonArrStr = @"[{\"name\":\"James\"},{\"name\":\"jim\"}]";
    NSString *jsonTreeArrStr = @"{\"user\":[{\"name\":\"James\"},{\"name\":\"jim\"}]}";
    
    NSData *jsonData = [jsonTreeArrStr dataUsingEncoding:NSUTF8StringEncoding];
    id jsonObj = [NSJSONSerialization JSONObjectWithData:jsonData options:NSJSONReadingAllowFragments error:nil];
    // 判断对象数据类型
    if([jsonObj isKindOfClass:[NSDictionary class]]){
        // 字典类型
        NSDictionary *dic1 = (NSDictionary *)jsonObj;
        
        NSArray *arr = [dic1 objectForKey:@"user"];
        
        for (NSDictionary *dic in arr){
            _tvParseResult.text = [_tvParseResult.text stringByAppendingString: [dic objectForKey: @"name"]];
            _tvParseResult.text = [_tvParseResult.text stringByAppendingString: @"\n"];
        }
        
        //        NSDictionary *dic = [dic1 objectForKey:@"user"];
        //        _tvParseResult.text = [_tvParseResult.text stringByAppendingString: [dic objectForKey: @"name"]];
        //        _tvParseResult.text = [_tvParseResult.text stringByAppendingString: @"\n"];
        //        _tvParseResult.text = [_tvParseResult.text stringByAppendingString: [dic objectForKey: @"age"]];
    }
    if([jsonObj isKindOfClass:[NSArray class]]){
        // 数组类型
        NSArray *arr = (NSArray *)jsonObj;
        
        for (NSDictionary *dic in arr){
            _tvParseResult.text = [_tvParseResult.text stringByAppendingString: [dic objectForKey: @"name"]];
            _tvParseResult.text = [_tvParseResult.text stringByAppendingString: @"\n"];
        }
    }
}

2-3 JSON解析案例二

代码演示:

/*
 iOS5+自带JSON操作库
 
 数据解析:
    要求:分别解析以下JSON数据
        {"name":"James","age":"30"}
        {"user":{"name":"James","age":"30"}}
        [{"name":"James"},{"name":"jim"}]
        {"user":[{"name":"James"},{"name":"jim"}]}
    目的:掌握通过NSJSONSerialization类解析JSON数据
    重点:掌握静态函数JSONObjectWithData:options:error:的使用
 */
// 解析JSON数据从字符串
- (void)jsonOnStr{
    _tvParseResult.text = [_tvParseResult.text stringByAppendingString: @"\n"];
    
    //NSString *jsonStr = @"{\"name\":\"James\",\"age\":\"30\"}";
    //NSString *jsonTreeStr = @"{\"user\":{\"name\":\"James\",\"age\":\"30\"}}";
    //NSString *jsonArrStr = @"[{\"name\":\"James\"},{\"name\":\"jim\"}]";
    NSString *jsonTreeArrStr = @"{\"user\":[{\"name\":\"James\"},{\"name\":\"jim\"}]}";
    
    NSData *jsonData = [jsonTreeArrStr dataUsingEncoding:NSUTF8StringEncoding];
    id jsonObj = [NSJSONSerialization JSONObjectWithData:jsonData options:NSJSONReadingAllowFragments error:nil];
    // 判断对象数据类型
    if([jsonObj isKindOfClass:[NSDictionary class]]){
        // 字典类型
        NSDictionary *dic1 = (NSDictionary *)jsonObj;
        
        NSArray *arr = [dic1 objectForKey:@"user"];
        
        for (NSDictionary *dic in arr){
            _tvParseResult.text = [_tvParseResult.text stringByAppendingString: [dic objectForKey: @"name"]];
            _tvParseResult.text = [_tvParseResult.text stringByAppendingString: @"\n"];
        }
        
        //        NSDictionary *dic = [dic1 objectForKey:@"user"];
        //        _tvParseResult.text = [_tvParseResult.text stringByAppendingString: [dic objectForKey: @"name"]];
        //        _tvParseResult.text = [_tvParseResult.text stringByAppendingString: @"\n"];
        //        _tvParseResult.text = [_tvParseResult.text stringByAppendingString: [dic objectForKey: @"age"]];
    }
    if([jsonObj isKindOfClass:[NSArray class]]){
        // 数组类型
        NSArray *arr = (NSArray *)jsonObj;
        
        for (NSDictionary *dic in arr){
            _tvParseResult.text = [_tvParseResult.text stringByAppendingString: [dic objectForKey: @"name"]];
            _tvParseResult.text = [_tvParseResult.text stringByAppendingString: @"\n"];
        }
    }
}

2-4 JSON解析案例三

代码演示:

/*
 iOS5+自带JSON操作库
 
 数据解析:
    要求:分别解析以下JSON数据
        {"name":"James","age":"30"}
        {"user":{"name":"James","age":"30"}}
        [{"name":"James"},{"name":"jim"}]
        {"user":[{"name":"James"},{"name":"jim"}]}
    目的:掌握通过NSJSONSerialization类解析JSON数据
    重点:掌握静态函数JSONObjectWithData:options:error:的使用
 */
// 解析JSON数据从字符串
- (void)jsonOnStr{
    _tvParseResult.text = [_tvParseResult.text stringByAppendingString: @"\n"];
    
    //NSString *jsonStr = @"{\"name\":\"James\",\"age\":\"30\"}";
    //NSString *jsonTreeStr = @"{\"user\":{\"name\":\"James\",\"age\":\"30\"}}";
    //NSString *jsonArrStr = @"[{\"name\":\"James\"},{\"name\":\"jim\"}]";
    NSString *jsonTreeArrStr = @"{\"user\":[{\"name\":\"James\"},{\"name\":\"jim\"}]}";
    
    NSData *jsonData = [jsonTreeArrStr dataUsingEncoding:NSUTF8StringEncoding];
    id jsonObj = [NSJSONSerialization JSONObjectWithData:jsonData options:NSJSONReadingAllowFragments error:nil];
    // 判断对象数据类型
    if([jsonObj isKindOfClass:[NSDictionary class]]){
        // 字典类型
        NSDictionary *dic1 = (NSDictionary *)jsonObj;
        
        NSArray *arr = [dic1 objectForKey:@"user"];
        
        for (NSDictionary *dic in arr){
            _tvParseResult.text = [_tvParseResult.text stringByAppendingString: [dic objectForKey: @"name"]];
            _tvParseResult.text = [_tvParseResult.text stringByAppendingString: @"\n"];
        }
        
        //        NSDictionary *dic = [dic1 objectForKey:@"user"];
        //        _tvParseResult.text = [_tvParseResult.text stringByAppendingString: [dic objectForKey: @"name"]];
        //        _tvParseResult.text = [_tvParseResult.text stringByAppendingString: @"\n"];
        //        _tvParseResult.text = [_tvParseResult.text stringByAppendingString: [dic objectForKey: @"age"]];
    }
    if([jsonObj isKindOfClass:[NSArray class]]){
        // 数组类型
        NSArray *arr = (NSArray *)jsonObj;
        
        for (NSDictionary *dic in arr){
            _tvParseResult.text = [_tvParseResult.text stringByAppendingString: [dic objectForKey: @"name"]];
            _tvParseResult.text = [_tvParseResult.text stringByAppendingString: @"\n"];
        }
    }
}

2-5 JSON读取文件

代码演示:

/*
 iOS5+自带JSON操作库
 
 数据解析:
 要求:1.从文件读取json数据并解析,文件名称weatherinfo.json
 2.从网络读取json数据并解析,http://www.weather.com.cn/data/cityinfo/101010100.html
 目的:掌握通过NSJSONSerialization类解析来自文件和网络的JSON数据
 重点:掌握静态函数JSONObjectWithData:options:error:的使用,灵活掌握json的数据源读取技巧
 */
// 解析JSON数据从文件
- (void)jsonOnFile{
    _tvParseResult.text = [_tvParseResult.text stringByAppendingString: @"\n"];
    
    NSString *filePath = [[NSBundle mainBundle] pathForResource:@"weatherinfo" ofType:@"json"];
    
    NSFileManager *fileMgr = [NSFileManager defaultManager];
    
    NSString *jsonStr;
    
    if([fileMgr fileExistsAtPath:filePath]){
        
        jsonStr = [NSString stringWithContentsOfFile:filePath encoding:NSUTF8StringEncoding error:nil];
        
    }else{
        _tvParseResult.text = [_tvParseResult.text stringByAppendingString: @"文件没有找到"];
        return;
    }
    
    NSData *jsonData = [jsonStr dataUsingEncoding:NSUTF8StringEncoding];
    id jsonObj = [NSJSONSerialization JSONObjectWithData:jsonData options:NSJSONReadingAllowFragments error:nil];
    // 判断对象数据类型
    if([jsonObj isKindOfClass:[NSDictionary class]]){
        // 字典类型
        NSDictionary *dic1 = (NSDictionary *)jsonObj;
        NSDictionary *dic = [dic1 objectForKey:@"weatherinfo"];
        
        _tvParseResult.text = [_tvParseResult.text stringByAppendingString: [dic objectForKey: @"city"]];
        _tvParseResult.text = [_tvParseResult.text stringByAppendingString: @"\n"];
        _tvParseResult.text = [_tvParseResult.text stringByAppendingString: [dic objectForKey: @"temp1"]];
        _tvParseResult.text = [_tvParseResult.text stringByAppendingString: @"\n"];
        _tvParseResult.text = [_tvParseResult.text stringByAppendingString: [dic objectForKey: @"temp2"]];
        _tvParseResult.text = [_tvParseResult.text stringByAppendingString: @"\n"];
        _tvParseResult.text = [_tvParseResult.text stringByAppendingString: [dic objectForKey: @"weather"]];
        
    }
    if([jsonObj isKindOfClass:[NSArray class]]){
        // 数组类型
        NSArray *arr = (NSArray *)jsonObj;
        
        for (NSDictionary *dic in arr){
            _tvParseResult.text = [_tvParseResult.text stringByAppendingString: [dic objectForKey: @"name"]];
            _tvParseResult.text = [_tvParseResult.text stringByAppendingString: @"\n"];
        }
    }
    
}

2-6 JSON网络解析

代码演示:

/*
 iOS5+自带JSON操作库
 
 数据解析:
    要求:1.从文件读取json数据并解析,文件名称weatherinfo.json
         2.从网络读取json数据并解析,http://www.weather.com.cn/data/cityinfo/101010100.html
    目的:掌握通过NSJSONSerialization类解析来自文件和网络的JSON数据
    重点:掌握静态函数JSONObjectWithData:options:error:的使用,灵活掌握json的数据源读取技巧
 */
// 解析JSON数据从文件
- (void)jsonOnUrl{
    _tvParseResult.text = [_tvParseResult.text stringByAppendingString: @"\n"];
    
    // 加载网络资源方式一
    NSURL *url = [NSURL URLWithString:@"http://www.weather.com.cn/data/cityinfo/101010100.html"];
    //NSData *jsonData = [NSData dataWithContentsOfURL:url];
    
    // 加载网络资源方式二
    NSString *jsonStr = [NSString stringWithContentsOfURL:url encoding:NSUTF8StringEncoding error:nil];
    NSData *jsonData = [jsonStr dataUsingEncoding:NSUTF8StringEncoding];
    
    // 加载网络资源方式三
    /*
    NSURLRequest *request = [[NSURLRequest alloc] initWithURL:url];
    NSURLSession *session = [NSURLSession sharedSession];
    // 根据会话对象,创建一个Task任务
    NSURLSessionTask *sessionDataTask = [session dataTaskWithRequest:request completionHandler:^(NSData * _Nullable data,NSURLResponse * _Nullable response, NSError * _Nullable error){
        
        // 解析响应数据
        //NSLog(@"从服务器获取到数据,响应消息:%@",[[NSString alloc] initWithData:data encoding:NSUTF8StringEncoding]);
        
        // 解析JOSN数据
        id obj = [NSJSONSerialization JSONObjectWithData:data options:0 error:nil];
        //NSLog(@"从服务器获取到数据,响应消息:%@",obj);
        // 如果obj是 字典类型
        if([obj isKindOfClass:[NSDictionary class]]){
            NSDictionary *weatherinfo = [(NSDictionary *)obj objectForKey:@"weatherinfo"];
            NSLog(@"weatherinfo:%@",weatherinfo);
        }
        
    }];
    
    // 执行任务
    [sessionDataTask resume];
    */
     
    id jsonObj = [NSJSONSerialization JSONObjectWithData:jsonData options:NSJSONReadingAllowFragments error:nil];
    // 判断对象数据类型
    if([jsonObj isKindOfClass:[NSDictionary class]]){
        // 字典类型
        NSDictionary *dic1 = (NSDictionary *)jsonObj;
        NSDictionary *dic = [dic1 objectForKey:@"weatherinfo"];
        
        _tvParseResult.text = [_tvParseResult.text stringByAppendingString: [dic objectForKey: @"city"]];
        _tvParseResult.text = [_tvParseResult.text stringByAppendingString: @"\n"];
        _tvParseResult.text = [_tvParseResult.text stringByAppendingString: [dic objectForKey: @"temp1"]];
        _tvParseResult.text = [_tvParseResult.text stringByAppendingString: @"\n"];
        _tvParseResult.text = [_tvParseResult.text stringByAppendingString: [dic objectForKey: @"temp2"]];
        _tvParseResult.text = [_tvParseResult.text stringByAppendingString: @"\n"];
        _tvParseResult.text = [_tvParseResult.text stringByAppendingString: [dic objectForKey: @"weather"]];

    }
    if([jsonObj isKindOfClass:[NSArray class]]){
        // 数组类型
        NSArray *arr = (NSArray *)jsonObj;
        
        for (NSDictionary *dic in arr){
            _tvParseResult.text = [_tvParseResult.text stringByAppendingString: [dic objectForKey: @"name"]];
            _tvParseResult.text = [_tvParseResult.text stringByAppendingString: @"\n"];
        }
    }

}

2-7 JSONKit解析JSON数据

使用JSONKit解析JSON数据

// 导入JSONKit库
#import “JSONKit.h”
// 实例化解析器
JSONDecoder *jsonDecoder = [[JSONDecoder alloc] init];
// 解析数据
id jsonObj = [jsonDecoder objectWithData:jsonData];

2-8 TouchJSON

使用TouchJSON解析JSON数据

// 导入JSONKit库
#import “CJSONDeserializer.h”
// 实例化解析器
CJSONDeserializer *des = [CJSONDeserializer deserializer];
// 解析数据
id jsonObj = [des deserialize: jsonData error: nil];

2-9 SBJson

使用SBJson解析JSON数据

// 导入SBJson库
#import “SBJsonParser.h”
// 实例化解析器
SBJsonParser *jsonParser= [[SBJsonParser alloc] init];
// 解析数据
id jsonObj = [jsonParser objectWithData:jsonData];

JSON数据解析总结

1.优先使用iOS自带解析器
    1)自带解析器(类方法) 类名:NSJSONSerialization 方法:JSONObjectWithData:option:error:
    2)JSOKit 类名:JSONDecoder 方法:objectWithData:
    3)TouchJson 类名:CJSONDeserializer方法:deserialize:error:
    4)SBJson 类名:SBJsonParser方法:objectWithData:
2.第三方库使用步骤
    1)下载并拷贝到工程路径下
    2)以create group方式导入工程
    3)如果工程使用ARC,则针对导入的源文件使用-fno-objc-arc命令
3.json数据解析步骤
    1)从数据源获取json数据
    2)将json数据转换为NSDictionary或NSArray
    3)解析NSDictionary或NSArray
    

第三章:XML简介和数据解析

3-1 XML介绍

什么是XML

XML:Extensible Markup Language 可扩展标记语言

XML语法

clipboard.png

XML嵌套叠加

clipboard.png

XML语义分析

clipboard.png

示例:组织信息为XML

clipboard.png

clipboard.png

3-2 SAX解析XML案例一

XML解析

3-3 SAX解析XML案例二

代码演示:

//
//  ViewController.m
//  MyXmlSax
//
//  Created by zc on 2017/6/2.
//  Copyright © 2017年 com.zccoder. All rights reserved.
//

/*
 XML解析
 
 要求解析以下XML字符串
    a.<info>James</info>
    b.<info name="James"></info>
    c.<info><name>James</name></info>
    d.<info><name>James</name><name>Jim</name></info>
 目的
    1.掌握使用SAX(Simple API for XML)方式解析XML
    2.了解SAX解析XML的基本原理
 重点
    1.NSXMLParser类的使用
    2.5个代理函数
        a. - (void)parserDidStartDocument:(NSXMLParser *)parser //准备解析
        b. - (void)parser:(NSXMLParser *)parser didStartElement:(NSString *)elementName namespaceURI:
            (NSString *)namespaceURI qualifiedName:(NSString *)qName attributes:(NSDictionary<NSString *,NSString *> *)
            attributeDict //准备解析当前节点
        c. - (void)parser:(NSXMLParser *)parser foundCharacters:(NSString *)string // 获取收尾节点间内容
        d. - (void)parser:(NSXMLParser *)parser didEndElement:(NSString *)elementName namespaceURI:
            (NSString *)namespaceURI qualifiedName:(NSString *)qName // 解析完当前节点
        e. - (void)parserDidEndDocument:(NSXMLParser *)parser // 解析结束
 
 */

#import "ViewController.h"

@interface ViewController ()

@end

@implementation ViewController

- (void)viewDidLoad {
    [super viewDidLoad];
    // Do any additional setup after loading the view, typically from a nib.
}


- (void)didReceiveMemoryWarning {
    [super didReceiveMemoryWarning];
    // Dispose of any resources that can be recreated.
}

// 解析数据按钮点击事件
- (IBAction)onParse:(id)sender {
    //NSString *xmlStr1 = @"<info>James</info>";
    //NSString *xmlStr2 = @"<info name=\"James\"></info>";
    //NSString *xmlStr3 = @"<info><name>James</name></info>";
    NSString *xmlStr4 = @"<info><name>James</name><name>Jim</name></info>";
    
    NSData *xmlDaTa = [xmlStr4 dataUsingEncoding:NSUTF8StringEncoding];
    NSXMLParser *xmlParser = [[NSXMLParser alloc] initWithData:xmlDaTa];
    xmlParser.delegate = self;
    [xmlParser parse];
}

// 准备解析
- (void)parserDidStartDocument:(NSXMLParser *)parser{
    [self appendPrintln];
    _tvParseResult.text = [_tvParseResult.text stringByAppendingString:@"准备解析"];
    
}
// 准备解析当前节点
- (void)parser:(NSXMLParser *)parser didStartElement:(NSString *)elementName namespaceURI:(NSString *)namespaceURI qualifiedName:(NSString *)qName attributes:(NSDictionary<NSString *,NSString *> *)attributeDict{
    [self appendPrintln];
    _tvParseResult.text = [_tvParseResult.text stringByAppendingString:@"准备解析当前节点为:"];
    _tvParseResult.text = [_tvParseResult.text stringByAppendingString:elementName];
    //[self appendPrintln];
    //_tvParseResult.text = [_tvParseResult.text stringByAppendingString:@"属性值为:"];
    //_tvParseResult.text = [_tvParseResult.text stringByAppendingString:[attributeDict objectForKey:@"name"]];

}
// 获取首尾节点间内容
- (void)parser:(NSXMLParser *)parser foundCharacters:(NSString *)string{
    [self appendPrintln];
    _tvParseResult.text = [_tvParseResult.text stringByAppendingString:string];

}
// 解析完当前节点
- (void)parser:(NSXMLParser *)parser didEndElement:(NSString *)elementName namespaceURI:(NSString *)namespaceURI qualifiedName:(NSString *)qName{
    [self appendPrintln];
    _tvParseResult.text = [_tvParseResult.text stringByAppendingString:@"解析完当前节点"];
}
// 解析结束
- (void)parserDidEndDocument:(NSXMLParser *)parser{
    [self appendPrintln];
    _tvParseResult.text = [_tvParseResult.text stringByAppendingString:@"结束解析"];
}

- (void)appendPrintln{
    _tvParseResult.text = [_tvParseResult.text stringByAppendingString:@"\n"];
}

@end

3-4 DOM解析XML

代码截图

clipboard.png

第四章:总结

4-1 总结

DOM适于解析比较简单的XML而SAX则适于解析较复杂的XML文件。各有各的好。
DOM和SAX的不同:

 1. DOM是基于内存的,不管文件有多大,都会将所有的内容预先装载到内存中。从而消耗很大的内存空间。而SAX是基于事件的。当某个事件被触发时,才获取相应的XML的部分数据,从而不管XML文件有多大,都只占用了少量的内存空间。
 2. DOM可以读取XML也可以向XML文件中插入数据,而SAX却只能对XML进行读取,而不能在文件中插入数据。这也是SAX的一个缺点。
 3. SAX的另一个缺点:DOM我们可以指定要访问的元素进行随机访问,而SAX则不行。SAX是从文档开始执行遍历的。并且只能遍历一次。也就是说我们不能随机的访问XML文件,只能从头到尾的将XML文件遍历一次(当然也可以中间截断遍历)。

妙手空空
1.3k 声望370 粉丝

博观而约取,厚积而薄发