将NSString转换为NSDictionary

5

有没有一种方法可以从通过其description方法创建的字符串中获取NSDictionary

给定以下代码:

NSDictionary *dictionary = [NSDictionary dictionaryWithObjects:[NSArray arrayWithObjects:@"value 1", @"value 2", nil] forKeys:[NSArray arrayWithObjects:@"key 1", @"key 2", nil]];
NSString *dictionaryString = [dictionary description];
NSLog(dictionaryString);

这将生成以下输出结果:
{
    "key 1" = "value 1";
    "key 2" = "value 2";
}

有没有一种简单的方法可以从字符串返回到NSDictionary?

2
为什么不使用序列化代替描述字段? - Kekoa
3
NSLog(dictionaryString); 是一个安全问题。使用 NSLog(@"%@", dictionaryString); 代替。如果 dictionaryString 包含字符 %@,你的应用程序将会崩溃或者泄露潜在敏感信息。 - Jon Hess
4个回答

6
冒昧问一句:你为什么想要这样做?如果你想在文本和其他格式之间进行转换,请使用NSPropertyListSerialization类。

1
我打出这个示例只是为了清楚地展示我正在尝试解析的字符串。实话实说,“字典字符串”来自于一个3.0 API而不是我的代码。我认为可能有一种简单的方法来解析它。 - Lounges
1
也许它实际上是OpenStep格式的属性列表(这就是-[NSDictionary description]的作用,除了它允许非属性列表对象)。尝试使用NSPropertyListSerialization和该格式。 - Peter Hosey
4
+1 谢谢,运行良好。如果有人正在寻找示例,请注意:NSError* error; NSPropertyListFormat plistFormat; NSDictionary *temp = [NSPropertyListSerialization propertyListWithData:data options:NSPropertyListImmutable format:&plistFormat error:&error]; - Dexter
NSPropertyListSerialization不支持文本,它仅支持NSData。因此,在问题“将NSString转换为NSDictionary”上它会失败。 - Adam

5
短答案是否定的。描述文本旨在快速描述字典内容,通常用于调试目的。
可能(但不建议)解析输出字符串并将其用于填充新字典,但有许多情况下这种方法不起作用。例如,如果原始字典包含任何自定义数据类型,则描述输出将类似于:
{
    "key 1" = <SomeClass 0x31415927>;
    "key 2" = <SomeClass 0x42424242>;
}

当然,这是不可逆的。

从苹果开发者文档中关于NSDictionarydescription方法的说明:

如果接收器中的每个键都是NSString对象,则按键升序列出条目;否则,列出条目的顺序是未定义的。此方法旨在生成可读的调试输出,而不是用于序列化数据。如果您想存储字典数据以供以后检索,请参阅属性列表编程指南Cocoa档案和序列化编程指南


2
    NSDictionary *dictionary = [NSDictionary dictionaryWithObjects:[NSArray arrayWithObjects:@"value 1", @"value 2", nil] forKeys:[NSArray arrayWithObjects:@"key 1", @"key 2", nil]];
    NSString *dictionaryString = [dictionary description];
    NSLog(@"%@", dictionaryString);

    NSDictionary *d = [dictionaryString propertyList];
    NSLog(@"%@", [d objectForKey:@"key 2"]);

请注意,苹果的文档指出:
/* 由于这些方法无法与二进制属性列表和字符串文件配合使用,因此不再推荐使用。请改用NSPropertyList.h中的API。
*/
然而,如果您知道或可以验证您没有传递二进制格式,则此方法应该可以正常使用。

1

我认为没有现成的方法,但你可以通过枚举字符串内容来编写一个方法,这看起来是一个相当容易的格式。


不是一个好主意。尽管这段代码的格式看起来很简单,但你不能总是依赖引号甚至精确的格式。 - Quinn Taylor

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接