TouchJSON,处理 NSNull
你好 我正在使用 TouchJSON 反序列化一些 JSON。我过去一直在使用它,并且在那些情况下我手动处理 NSNull 的出现。我认为作者也必须处理这个问题,所以我再次这样做只会产生开销。然后我在文档中找到了这个:
避免输出中的 NSNull 值。
NSData *theJSONData = /* some JSON data */
CJSONDeserializer *theDeserializer = [CJSONDeserializer deserializer];
theDeserializer.nullObject = NULL;
NSError *theError = nil;
id theObject = [theDeserializer deserialize:theJSONData error:&theError];}
按照我的理解,类的用户可以将 C 风格的空指针传递给反序列化器,当它遇到 NSNull 时,它将插入传递给它的值 (NULL)。所以稍后当我使用这些值时,我不会得到 NSNull,而是 NULL。
这看起来很奇怪,返回值是一个只能包含对象的 NSDictionary,该值不应该默认为“nil”吗?
如果它是 NULL,我可以检查这样的值吗?
if([jsonDataDict objectForKey:someKey] == NULL)
能够做到这一点似乎更符合逻辑:
if(![jsonDataDict objectForKey:someKey])
更不用说允许传递 nil 但传递 NULL 会导致崩溃的所有情况。
或者我可以将“nil”传递给反序列化器吗?
这很大程度上源于我仍在与 nil、NULL、[NSNULL null] 作斗争,也许我没有看到使用 nil 的潜在警告。
Hi
I am using TouchJSON to deserialize some JSON. I have been using it in the past and on those occasions I dealt with occurrences of NSNull manually. I would think the author had to deal with this as well, so me doing that again would just be overhead. I then found this in the documentation:
Avoiding NSNull values in output.
NSData *theJSONData = /* some JSON data */
CJSONDeserializer *theDeserializer = [CJSONDeserializer deserializer];
theDeserializer.nullObject = NULL;
NSError *theError = nil;
id theObject = [theDeserializer deserialize:theJSONData error:&theError];}
The way I understand it the user of the class can pass a C-style null pointer to the deserializer and when it encounters a NSNull it will insert the values (NULL) passed to it. So later on when I use the values I won't get NSNull, but NULL.
This seems strange, the return value is an NSDictionary which can only contain Objects, shouldn't the value default to 'nil' instead?
If it is NULL can I check the values like this?
if([jsonDataDict objectForKey:someKey] == NULL)
It would seem more logically to be able to do this:
if(![jsonDataDict objectForKey:someKey])
No to mention all the cases where passing nil is allowed but passing NULL causes a crash.
Or can I just pass 'nil' to the deserializer?
Much of this stems from me still struggling with nil, NULL, [NSNULL null], maybe I am failing to see the potential caveats in using nil.
如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。
绑定邮箱获取回复消息
由于您还没有绑定你的真实邮箱,如果其他用户或者作者回复了您的评论,将不能在第一时间通知您!
发布评论
评论(3)
对于另一个 JSON 库,但遇到同样的问题,我在 NSDictionary 上创建了以下类别:
每当我处理来自所述库的 JSON 数据时,我都会检索如下值:
这样,我的项目中的代码变得更加干净,并且同时我不必考虑处理 [NSNull null] 值等。
For another JSON library, but with the same issues, I've created the following category on NSDictionary:
Whenever I deal with JSON data from said library, I retrieve values like this:
This way the code in my projects become a lot cleaner and at the same time I don't have to think about dealing with [NSNull null] values and the like.
nil
和NULL
实际上都等于零,因此实际上它们是可以互换的。但你是对的,为了保持一致性,TouchJSON 的文档应该使用theDeserializer.nullObject = nil
而不是NULL
。现在,当您这样做时,您的第二个谓词实际上可以正常工作:
因为当您将
nullObject
设置为nil
(或NULL< /代码>)。当字典中不存在该键时,NSDictionary 返回 nil,它为零,因此您的 if 条件按您的预期工作。
如果您没有将
nullObject
指定为nil
,则可以像这样检查 null:nil
andNULL
are actually both equal to zero, so they are, in practice, interchangeable. But you're right, for consistency, the documentation for TouchJSON should have usedtheDeserializer.nullObject = nil
instead ofNULL
.Now, when you do that, your second predicate actually works fine:
because TouchJSON omits the key from the dictionary when you have
nullObject
set tonil
(orNULL
). When the key doesn't exist in the dictionary, NSDictionary returns nil, which is zero so your if condition works as you expect.If you don't specify
nullObject
asnil
, you can instead check for null like so:有一些库可以处理它。其中之一是Swift中的SwiftyJSON,另一个是Objective-C 中的“https://github.com/bernikowich/NSTEasyJSON” rel="nofollow noreferrer">NSTEasyJSON。
有了这个库(NSTEasyJSON),就可以轻松处理此类问题。在你的情况下,你可以只检查你需要的值:
这个值将是
NSString
或nil
并且你不应该自己检查它是否为 NSNull, NULL。There are libraries which deal with it. One of them is SwiftyJSON in Swift, another one is NSTEasyJSON in Objective-C.
With this library (NSTEasyJSON) it will be easy to deal with such problems. In your case you can just check values you need:
This value will be
NSString
ornil
and you should not check it for NSNull, NULL yourself.