【问题标题】:How to check if NSDictionary key is NULL如何检查 NSDictionary 键是否为 NULL
【发布时间】:2014-09-18 08:19:08
【问题描述】:

我正在尝试检查我的 JSON 响应字典中的键 next_max_id 是否存在对象。 我尝试了以下方法来检查:

  • if ([[pagination objectForKey:@"next_max_id"] isKindOfClass:[NSNull class]]) ...
  • if ([pagination objectForKey:@"next_max_id"] == [NSNull class]) ...
  • if ([pagination objectForKey:@"next_max_id"]) ...

但是,当分页字典为空时,即 (pagination = {};),我收到以下错误消息:

-[NSNull objectForKey:]: unrecognized selector sent to instance ...
*** Terminating app due to uncaught exception 'NSInvalidArgumentException', reason: '-[NSNull objectForKey:]: unrecognized selector sent to instance ...

我还能如何检查对象或键是否存在而不发生崩溃?

更新: 当密钥next_max_id 存在于pagination 中时,JSON 响应将是这样的

"pagination": {
    "next_url": "https://api.instagram.com/v1/tags/puppy/media/recent?access_token=fb2e77d.47a0479900504cb3ab4a1f626d174d2d&max_id=13872296",
    "next_max_id": "13872296"
}

【问题讨论】:

  • 如果字典中键 next_max_id 的对象为空,则键 next_max_id 是否可用
  • next_max_id 如果没有值则不存在。 JSON 响应将是这样的 pagination = {};

标签: ios objective-c afnetworking-2


【解决方案1】:
if( [pagination objectForKey:@"your_key"] == nil ||  
    [[pagination objectForKey:@"your_key"] isEqual:[NSNull null]] ){
    //nil dictionary
}

【讨论】:

    【解决方案2】:

    根据您描述的错误,分页不是 NSDictionary,但分页本身是 NSNull 对象。所以在其他所有事情之前的第一次检查将是

    if (pagination == [NSNull null]) ...
    

    如果您的 JSON 数据包含 "pagination": {} 则不会发生这种情况,但如果您的 JSON 数据包含 "pagination": null 则会发生这种情况。

    【讨论】:

      【解决方案3】:

      这样检查

      [pagination objectForKey:@"next_max_id"] == [NSNull null]
      

      如果这不起作用,请尝试

      [pagination objectForKey:@"next_max_id"] == (id)[NSNull null]
      

      【讨论】:

        【解决方案4】:

        实际的问题是paginationnil,你不能真正通过NSNull 调用任何选择器。正如您所提到的 - 只有当 pagination JSON 为空时才会出现问题 - 因此您会得到一个 nil 对象。

        所以,

        if (pagination && ![pagination isKindOfClass:[NSNull class]]) {
            ... // Do your things
        }
        

        如果分页是一个有效的NSDictionary 对象,objectForKey: 不存在的键将返回nil

        【讨论】:

          【解决方案5】:

          检查密钥是否存在:

          if([pagination objectForKey:@"next_max_id"] != nil) {
             // exists
          }
          else {
             // not exists
          }
          

          检查key是否存在且值为null

          if([pagination objectForKey:@"next_max_id"] == [NSNull null]) {
             // {"next_max_id":null, ...}
          }
          else {
             // not exists or values is not null
          }
          

          【讨论】:

            【解决方案6】:

            例如我创建了这个演示,你可以根据你修改

            NSDictionary *pagination = 
            [[NSDictionary alloc] initWithObjectsAndKeys:
               @"https://api.instagram.com/v1/tags/puppy/media/recent?access_token=fb2e77d.47a0479900504cb3ab4a1f626d174d2d&max_id=13872296",@"next_url",
               @"65765343",@"next_max_id",   nil];
            
            NSArray *array = [NSArray arrayWithArray:[pagination allKeys]];
            
            if ( [array containsObject:@"next_max_id"] ) {
                NSLog( @"%@",[pagination valueForKey:@"next_max_id"] );
            } else {
                NSLog(@"Key is null");
            }
            

            【讨论】:

            • 应该有一个for循环。像下面这样的东西。 for (int i = 0; i
            【解决方案7】:
            if( [pagination objectForKey:@"next_max_id"] == nil ||  
                [[pagination objectForKey:@"next_max_id"] isEqual:[NSNull null]] ||
                [pagination objectForKey:@"next_max_id"] == [NSNull null])
            {
                NSLog(@"Key is null");
            }
            else
            {
                NSLog(@"%@",[pagination valueForKey:@"next_max_id"]);
            }
            

            【讨论】:

              【解决方案8】:

              一个非常优雅的解决方案是为 NSDictionary 编写一个快速的类别。

              例如:

              #import "NSDictionary+safe.h"
              
              @implementation NSDictionary (safeJSON)
              
              - (id)safeObjectForKey:(NSString *)key {
              
                  id object = [self objectForKey:key];
                  if (object == [NSNull null]) {
                      return nil;
                  } else {
                      return object;
                  }
              }
              
              @end
              

              rckoenes here 也提到了这一点。

              【讨论】:

                【解决方案9】:

                -[NSNull objectForKey:]: 无法识别的选择器发送到实例

                错误已经在你手中。

                当您调用[pagination objectForKey:] 时,它会调用-[NSNull objectForKey:]

                意思是,paginationNSNull 不是 NSDictionaryNSNull 没有可调用的 objectForKey: 方法。这就是你得到错误的原因:

                无法识别的选择器发送到实例

                您可以通过以下方式进行检查,

                if ([pagination isKindOfClass:[NSDictionary class]]) {
                    id value =[pagination objectForKey:@"key"];
                }
                

                【讨论】:

                  猜你喜欢
                  • 1970-01-01
                  • 1970-01-01
                  • 2013-07-18
                  • 2015-08-23
                  • 1970-01-01
                  • 1970-01-01
                  • 1970-01-01
                  • 1970-01-01
                  • 2013-08-21
                  相关资源
                  最近更新 更多