网络07——NSURLConnection04_简单JSON的解析
前面,我们获取到了数据,数据的格式是JSON字符串。那么我们如何把它转成我们的OC对象呢?这就是我们接下来学习的。
一、什么是JSON
JSON是一种轻量级的数据格式,一般用于数据交互
服务器返回给客户端的数据,一般都是JSON格式或者XML格式(文件下载除外)
JSON的格式很像OC中的字典和数组
{"name" : "jack", "age" : 10}
{"names" : ["jack", "rose", "jim"]}
标准JSON格式的注意点:key必须用双引号
要想从JSON中挖掘出具体数据,得对JSON进行解析
JSON 转换为 OC数据类型
二、JSON – OC 转换对照表
JSON | OC |
---|---|
大括号 { } | NSDictionary |
中括号 [ ] | NSArray |
双引号 ” “ | NSString |
数字 10、10.8 | NSNumber |
三、JSON解析方案
在iOS中,JSON的常见解析方案有4种
第三方框架:JSONKit、SBJson、TouchJSON(性能从左到右,越差)
苹果原生(自带):NSJSONSerialization(性能最好)
四、NSJSONSerialization的常见方法
4.1 JSON数据 → OC对象
//第一个参数:JSON的二进制数据
//第二个参数:
//第三个参数:错误信息
//NSJSONReadingOptions说明-----------
//NSJSONReadingMutableContainers = (1UL << 0), 可变字典和数组
//NSJSONReadingMutableLeaves = (1UL << 1), 内部所有的字符串都是可变的 ios7之后又问题 一般不用
//NSJSONReadingAllowFragments = (1UL << 2) 既不是字典也不是数组,则必须使用该枚举值
+ (id)JSONObjectWithData:(NSData *)data options:(NSJSONReadingOptions)opt error:(NSError **)error;
4.2 OC对象 → JSON数据
//第一个参数:要转换的OC对象
//第二个参数:选项NSJSONWritingPrettyPrinted 排版 美观
+ (NSData *)dataWithJSONObject:(id)obj options:(NSJSONWritingOptions)opt error:(NSError **)error;
使用例如
-(void)ocToJson{
NSArray *mode = @[@"123",@"456"];
NSData *data = [NSJSONSerialization dataWithJSONObject:mode options:NSJSONWritingPrettyPrinted error:nil];
NSLog(@"%@",[[NSString alloc]initWithData:data encoding:NSUTF8StringEncoding]);
}
注意:并不是所有的OC对象都能转换为JSON
最外层必须是 NSArray or NSDictionary
所有的元素必须是 NSString, NSNumber, NSArray, NSDictionary, or NSNull
字典中所有的key都必须是 NSString类型的
NSNumbers不能是无穷大
4.3 isValidJSONObject 判断OC能否转JSON
+ (BOOL)isValidJSONObject:(id)obj;
五、登陆接口的简单装换
5.1 分析
我们请求登陆接口 iOS学习笔记-143.网络03——自己搭建的后台登陆接口文档 后返回JSON类型的二进制数据。我们可以通过 NSJSONSerialization 上面说的的 + (id)JSONObjectWithData:(NSData *)data options:(NSJSONReadingOptions)opt error:(NSError **)error;
方法,把它转为OC对象,主要的代码是
NSDictionary * dict = [NSJSONSerialization JSONObjectWithData:data options:NSJSONReadingMutableContainers error:nil];
由前面,或者接口文档,我们可以知道,返回的数据转为字符串以后是如下的样子
{
"code": 200,
"msg": "登录成功",
"t": {
"userName": "qiwenming",
"clientType": "1"
}
}
那么我们上面转换的地址拿到的数据就这这个样子的。那么我们想要获取我们的 code,怎么获取呢??
可以通过字典拿到 dict[@”code”] 。其次我们的 t 又是一个字典,我们可以把它转为一个对象。
当然我们也可以这样,把最外城数据装换为一个OC对象,这个对象里面包含,我们的 t 这个oc 对象。
对应的,我们们创建了两个对应的类,分别是QWMLoginMode 和QWMLoginSuccessMode。
5.2 QWMLoginMode
5.2.1 QWMLoginMode.h
//
// QWMLoginMode.h
// 002_JSON解析
//
// Created by 杞文明 on 17/9/13.
// Copyright © 2017年 杞文明. All rights reserved.
//
#import <Foundation/Foundation.h>
#import "QWMLoginSuccessMode.h"
@interface QWMLoginMode : NSObject
@property(nonatomic,strong)NSString *msg;
@property(nonatomic,strong)NSNumber *code;
@property(nonatomic,strong)QWMLoginSuccessMode *t;
+(instancetype)initWithDict:(NSDictionary*)dict;
@end
5.2.2 QWMLoginMode.m
//
// QWMLoginMode.m
// 002_JSON解析
//
// Created by 杞文明 on 17/9/13.
// Copyright © 2017年 杞文明. All rights reserved.
//
#import "QWMLoginMode.h"
@implementation QWMLoginMode
+(instancetype)initWithDict:(NSDictionary*)dict{
QWMLoginMode * mode = [[QWMLoginMode alloc]init];
[mode setValuesForKeysWithDictionary:dict];
mode.t = [QWMLoginSuccessMode initWithDict:[dict valueForKey:@"t"]];
return mode;
}
@end
5.3 QWMLoginMode
5.3.1 QWMLoginMode.h
//
// QWMLoginSuccessMode.h
// 002_JSON解析
//
// Created by 杞文明 on 17/9/13.
// Copyright © 2017年 杞文明. All rights reserved.
//
#import <Foundation/Foundation.h>
@interface QWMLoginSuccessMode : NSObject
@property(nonatomic,strong)NSString* userName;
@property(nonatomic,strong)NSString* clientType;
+(instancetype)initWithDict:(NSDictionary*)dict;
@end
5.3.2 QWMLoginMode.m
//
// QWMLoginSuccessMode.m
// 002_JSON解析
//
// Created by 杞文明 on 17/9/13.
// Copyright © 2017年 杞文明. All rights reserved.
//
#import "QWMLoginSuccessMode.h"
@implementation QWMLoginSuccessMode
+(instancetype)initWithDict:(NSDictionary*)dict{
QWMLoginSuccessMode * mode = [[QWMLoginSuccessMode alloc]init];
[mode setValuesForKeysWithDictionary:dict];
return mode;
}
@end
5.4 控制器的代码
//
// ViewController.m
// 002_JSON解析
//
// Created by 杞文明 on 17/9/12.
// Copyright © 2017年 杞文明. All rights reserved.
//
#import "ViewController.h"
#import "NSString+MD5.h"
#import "QWMLoginMode.h"
//登陆请求地址
#define LOGINURL @"http://127.0.0.1:8080/qwmapi/login"
@interface ViewController ()
@end
@implementation ViewController
-(void)touchesBegan:(NSSet<UITouch *> *)touches withEvent:(UIEvent *)event{
[self jsonToOC];
// [self ocToJson];
}
-(void)jsonToOC{
//1.设置URL
NSURL *url = [NSURL URLWithString:LOGINURL];
//2.创建请求对象
NSMutableURLRequest *request = [NSMutableURLRequest requestWithURL:url];
//设置请求方法
request.HTTPMethod = @"POST";
//设置请求头
[request setValue:@"2" forHTTPHeaderField:@"QWM-CLIENT-TYPE"];
//设置请求体
NSString *params = [NSString stringWithFormat:@"userName=qiwenming&password=%@",[@"123456" MD5_32BitLower]];
request.HTTPBody = [params dataUsingEncoding:NSUTF8StringEncoding];
//3.发送异步请求
[NSURLConnection sendAsynchronousRequest:request queue:[NSOperationQueue mainQueue] completionHandler:^(NSURLResponse * _Nullable response, NSData * _Nullable data, NSError * _Nullable connectionError) {
/*
第一个参数:JSON的二进制数据
第二个参数:
第三个参数:错误信息
*/
/*
NSJSONReadingOptions------------------
NSJSONReadingMutableContainers = (1UL << 0), 可变字典和数组
NSJSONReadingMutableLeaves = (1UL << 1), 内部所有的字符串都是可变的 ios7之后又问题 一般不用
NSJSONReadingAllowFragments = (1UL << 2) 既不是字典也不是数组,则必须使用该枚举值
*/
NSDictionary * dict = [NSJSONSerialization JSONObjectWithData:data options:NSJSONReadingMutableContainers error:nil];
QWMLoginMode * mode =[QWMLoginMode initWithDict:dict];
NSLog(@"%@",mode.code);
NSLog(@"%@",mode.msg);
NSLog(@"%@",mode.t.clientType);
NSLog(@"%@",mode.t.userName);
}];
}
-(void)ocToJson{
// QWMLoginSuccessMode *mode = [[QWMLoginSuccessMode alloc]init];
// mode.clientType = @"1";
// mode.userName =@"wiming";
// NSString *mode = @"WENIDNGDING";
//注意:并不是所有的OC对象都能转换为JSON
/*
- 最外层必须是 NSArray or NSDictionary
- 所有的元素必须是 NSString, NSNumber, NSArray, NSDictionary, or NSNull
- 字典中所有的key都必须是 NSString类型的
- NSNumbers不能是无穷大
*/
NSArray *mode = @[@"123",@"456"];
NSData *data = [NSJSONSerialization dataWithJSONObject:mode options:NSJSONWritingPrettyPrinted error:nil];
NSLog(@"%@",[[NSString alloc]initWithData:data encoding:NSUTF8StringEncoding]);
}
@end
5.5 打印结果
[30895:167756] 200
[30895:167756] 登录成功
[30895:167756] 2
[30895:167756] qiwenming