将复杂的 NSObject 序列化为 JSON 模式

Posted

技术标签:

【中文标题】将复杂的 NSObject 序列化为 JSON 模式【英文标题】:Serializing complex NSObject to JSON pattern 【发布时间】:2012-02-08 17:18:47 【问题描述】:

我有一系列 NSObject,我想序列化为 JSON 并发布到服务。最终的对象由多个嵌套的这些 NSObject 子类组成。

这些对象中的每一个都遵循带有方法的协议,该方法使用适当的键在 NSDictionary 中返回该对象的属性。但是,其中一些属性是其他对象等等,使得序列化有点复杂。

有没有一种模式可以用来简化最终对象的序列化?使用 JSONKit,似乎我需要从最深的对象单独序列化每个字典并向后工作,检查错误,然后添加到复合字符串。我知道这不可能是使用这个功能强大的库的最佳方法。欢迎任何建议或指导。

编辑 1

JSONKit GitHub URL

JSONKit Readme Documentation

【问题讨论】:

您可以将任何对象(嗯,几乎)表示为属性列表,就像您在编写encodeWithCoder: 时所做的那样。代码可以一样,得到的NSDictionary可以序列化成JSON。 大多数 JSON 库只需告诉根对象进行编码即可非常轻松地对复杂数据结构进行深度序列化。如果JSONKit 不允许这样做,也许您需要不同的 JSON 库。 【参考方案1】:

AutomagicCoding 库使用低级属性自省将任何 NSObject 递归转换为 NSDictionary,然后可以直接序列化为 JSON:

https://github.com/psineur/NSObject-AutomagicCoding

它可能需要对具有结构等属性的类进行一些微调,但这可能是您能找到的最简单、最省力的方法。

更新:

我已经编写了自己的库 HRCoding (https://github.com/nicklockwood/HRCoder),它可以使用 NSCoding 协议将任何对象加载/保存为 JSON)

【讨论】:

是的,我做到了。固定的。谢谢!【参考方案2】:

现在您可以使用JSONModel 轻松解决此问题。 JSONModel 是一个基于 Class 对对象进行一般序列化/反序列化的库。你甚至可以对intshortfloat 等属性使用非nsobject。它还可以满足嵌套复杂的 JSON。它会为您处理错误检查。

鉴于此 JSON "firstname":"Jenson","surname":"Button"

反序列化示例。在头文件中:

#import "JSONModel.h"

@interface Person : JSONModel 
@property (nonatomic, strong) NSString* firstname;
@property (nonatomic, strong) NSString* surname;
@end

在实现文件中:

#import "JSONModelLib.h"
#import "yourPersonClass.h"

NSString *responseJSON = /*from somewhere*/;
Person *person = [[Person alloc] initWithString:responseJSON error:&err];
if (!err)

   NSLog(@"%@  %@", person.firstname, person.surname):

序列化示例。在实现文件中:

#import "JSONModelLib.h"
#import "yourPersonClass.h"

Person *person = [[Person alloc] init];
person.firstname = @"Jenson";
person.surname = @"Uee";

NSLog(@"%@", [person toJSONString]);

【讨论】:

如果你想要复杂的例子,比如深嵌套的 JSON,请告诉我 好的。我有一个来自服务器的 json 字符串:"type":"string","obj":xxx xxx 内容取决于是什么类型。它可以是 JSONObject 或 JSONArray。这可以实现吗?【参考方案3】:

我不确定我是否理解问题所在。您要求一种模式,但您似乎描述的是标准模式:

这些对象中的每一个都遵循带有方法的协议,该方法使用适当的键在 NSDictionary 中返回该对象的属性。

假设该方法称为serializedDictionary。如果一个类的属性本身就是其他对象,您只需调用serializedDictionary 并将结果添加到您正在构建的字典中。因此,您需要做的就是向***对象询问其serializedDictionary,并将其转换为 JSON。

如果您担心错误处理,只需检查方法的结果并将错误传递给调用者即可。您可以使用例外(无需编写代码)或按照约定来执行此操作。例如,假设在错误时返回 nil 并通过引用指向 NSError 实例的指针。然后在您的容器对象中执行以下操作:

- (NSDictionary *)serializedDictionaryWithError:(NSError **)error

    NSMutableDictionary *dict = [NSMutableDictionary dictionary];
    [dict setObject:self.someProperty forKey:@"some-property"];
    NSDictionary *childDict = [self.childObject serializedDictionaryWithError:error];
    if (childDict == nil) return nil;
    [dict setObject:childDict forKey:@"child-object"];
    return dict;

该死!

【讨论】:

以上是关于将复杂的 NSObject 序列化为 JSON 模式的主要内容,如果未能解决你的问题,请参考以下文章

将hal+json反序列化为复杂模型

如何使用 Flask 将复杂对象序列化为 JSON [重复]

将复杂的 json 文件反序列化为 POJO - 作为一个列表元素工作,或者不作为

无法将当前 JSON 数组(例如 [1,2,3])反序列化为具有复杂和嵌套对象的类型

C#使用Json

在Python 中如何将类对象序列化为JSON?