美文网首页
使用反射将自定义对象数据序列化成JSON数据

使用反射将自定义对象数据序列化成JSON数据

作者: twitter_me | 来源:发表于2016-01-13 11:54 被阅读454次

    NSJSONSerialization,这是一个非常好用的JSON生成和解析工具,效率也比其他第三方开源项目高。

    但用其生成JSON数据有个限制:只能将Foundation对象转换成JSON。即顶层对象必须是NSArray或者NSDictionary,所有的对象必须是NSString、NSNumber、NSArray、NSDictionary、NSNull的实例。

    所以,如果我们想要把自定义类型的数据对象转成JSON数据,NSJSONSerialization就无能为力了。

    1,将自定义对象转成JSON数据的实现原理(不借助第三方库)

    (1)首先我们使用反射(Reflection)对自定义类型的数据对象中所有的属性进行递归遍历,生成字典类型的数据并返回。

    (2)接着使用NSJSONSerialization就可以把这个字典类型的数据转换成jSON数据了。

    2,比如我们自定义一个的联系人类

    //用户类

    classUser{

    varname:String=""//姓名

    varnickname:String?//昵称

    varage:Int?//年龄

    varemails:[String]?//邮件地址

    vartels:[Telephone]?//电话

    }

    //电话结构体

    structTelephone{

    vartitle:String//电话标题

    varnumber:String//电话号码

    }

    3,JSON串生成的功能实现

    (1)首先定义一个叫JSON的协议,并对其扩展,实现协议中定义的两个方法。

    toJSONModel():将数据转成可用的JSON模型。

    toJSONString():将数据转成JSON字符串(其内部会调用前面的toJSONModel()方法)。

    (2)将可选类型(Optional),自定义类(User、TeleTelephone),以及基本数据类型进行扩展,使其遵循JSON协议。

    同时对于可选类型还要重写toJSONModel()方法,为的是当可选类型值不存在时返回nil,存在时将其转成具体类型并序列化

    //自定义一个JSON协议

    protocolJSON{

    functoJSONModel() ->AnyObject?

    functoJSONString() ->String?

    }

    //扩展协议方法

    extensionJSON{

    //将数据转成可用的JSON模型

    functoJSONModel() ->AnyObject? {

    letmirror =Mirror(reflecting:self)

    ifmirror.children.count > 0  {

    varresult: [String:AnyObject] = [:]

    forcaselet(label?, value)inmirror.children {

    //print("属性:\(label)     值:\(value)")

    ifletjsonValue = valueas?JSON{

    result[label] = jsonValue.toJSONModel()

    }

    }

    returnresult

    }

    returnselfas?AnyObject

    }

    //将数据转成JSON字符串

    functoJSONString() ->String? {

    letjsonModel =self.toJSONModel()

    //利用OC的json库转换成OC的NSData,

    letdata :NSData! = try?NSJSONSerialization.dataWithJSONObject(jsonModel!, options: [])

    //NSData转换成NSString打印输出

    letstr =NSString(data:data, encoding:NSUTF8StringEncoding)

    returnstrasString?

    }

    }

    //扩展可选类型,使其遵循JSON协议

    extensionOptional:JSON{

    //可选类型重写toJSONModel()方法

    functoJSONModel() ->AnyObject? {

    ifletx =self{

    ifletvalue = xas?JSON{

    returnvalue.toJSONModel()

    }

    }

    returnnil

    }

    }

    //扩展两个自定义类型,使其遵循JSON协议

    extensionUser:JSON{ }

    extensionTelephone:JSON{ }

    //扩展Swift的基本数据类型,使其遵循JSON协议

    extensionString:JSON{ }

    extensionInt:JSON{ }

    extensionBool:JSON{ }

    extensionDictionary:JSON{ }

    extensionArray:JSON{ }

    4,测试样例

    //创建一个User实例对象

    letuser1 =User()

    user1.name ="hangge"

    user1.age = 100

    user1.emails = ["hangge@hangge.com","system@hangge.com"]

    //添加动画

    lettel1 =Telephone(title:"手机", number:"123456")

    lettel2 =Telephone(title:"公司座机", number:"001-0358")

    user1.tels = [tel1, tel2]

    //输出json字符串

    print(user1.toJSONString()!)

    看到控制台输出如下信息:

    格式化后数据如下:

    {

    "tels": {

    "[1]": {

    "number": "001-0358",

    "title": "公司座机"

    },

    "[0]": {

    "number": "123456",

    "title": "手机"

    }

    },

    "age": 100,

    "name": "hangge",

    "emails": {

    "[1]": "system@hangge.com",

    "[0]": "hangge@hangge.com"

    }

    }

    原文出自:www.hangge.com转载请保留原文

    相关文章

      网友评论

          本文标题:使用反射将自定义对象数据序列化成JSON数据

          本文链接:https://www.haomeiwen.com/subject/zoyckttx.html