UITableView reloadData 崩溃并出现错误 [__NSCFConstantString objectForKey:]

Posted

技术标签:

【中文标题】UITableView reloadData 崩溃并出现错误 [__NSCFConstantString objectForKey:]【英文标题】:UITableView reloadData crashes with error [__NSCFConstantString objectForKey:] 【发布时间】:2012-10-08 07:28:55 【问题描述】:

我正在解析来自服务器的数据并在我的应用程序中显示这些数据。此数据是 JSON 数据,如下所示:

"getMessages":["msgid":"1","message":"Hello.","dateposted":"2012-08-28"]

此时可以发送消息,但是,如果没有消息可用,JSON 将如下所示:

"status":"No messages available"

在我的应用程序中,我使用 NSJSONSerialization 来解析 JSON。这是我的做法:

if ([data length] > 0)

   NSDictionary *parsedData = [NSJSONSerialization JSONObjectWithData:data options
   NSJSONReadingMutableContainers error:nil];

   if (![parsedData objectForKey:@"getMessages"])
   
      [self.messageArray addObject:@"No Messages"];
   
   else
   
      self.messageArray = (NSMutableArray *)[parsedData objectForKey:@"getMessages"];
   

如你所见,当parsedData没有getMessages键时,会在里面添加No Messages self.messageArray,但是如果它有key,它会添加与之相关的值。

self.messageArray 是我用来填充messageTable 的数组。在下载的最后,我输入了代码[messageTable reloadData]

问题是这样的:如果 parsedData 包含键 getMessages,则重新加载表有效。但是,如果未找到该键,则重新加载表会崩溃。

这是我的tableView:cellForRowAtIndexPath 方法:

NSString *tableIdentifier = @"Cell";
UITableViewCell *cell = [tableView dequeueReusableCellWithIdentifier:tableIdentifier];

if (cell == nil)
    cell = [[[UITableViewCell alloc]initWithStyle:UITableViewCellStyleSubtitle reuseIdentifier:tableIdentifier] autorelease];
if (tableView == messageTable) //I do this since there is another table I am using

    NSString *string = [NSString stringWithFormat:@"%@", [self.messageArray objectAtIndex:0]];

    if ([string isEqualToString:@"No Messages"])
    
        cell.textLabel.text = string;
    
    else
    
        NSDictionary *dict = [self.messageArray objectAtIndex:indexPath.row];
        cell.textLabel.text = [NSString stringWithFormat:@"%@", [dict objectForKey:@"message"]];
    

messageTable 中,我首先检查self.messageArray 的第一个索引是否等于字符串“No Messages”,这是为了让用户知道无法检索到任何消息。如果 string 不相等,它会假设数组中的数据是一个字典,因此,它会被解析以显示消息。

使用断点和日志后,我意识到崩溃是在重新加载表时发生的。我在 tableView:cellForRowAtIndexPath 方法的开头插入了一个断点和一个日志,但它甚至没有到达那里。我尝试检查self.messageArray 的内容,它确实包含“无消息”。

崩溃告诉我这个错误:[__NSCFConstantString objectForKey:]: unrecognized selector sent to instance 0x10ed84

我知道这个错误告诉我我正在调用 NSString 中的方法 objectForKey,但我真的不知道为什么。有人可以帮我吗?

【问题讨论】:

是你的代码在这一行崩溃了 - NSString *string = [NSString stringWithFormat:@"%@", [self.messageArray objectAtIndex:0]]; ?还是在这之后?哪条线崩溃了?检查第一个... 创建解析后的数据尝试记录 @Sharanya 没有代码在到达cellForRowAtIndexPath 之前就崩溃了。我在填充数组后立即检查了它,它工作正常。 ok then.. 检查 numberOfRowsInSection 方法中数组的计数.. 打印数组计数并检查何时没有消息.. 【参考方案1】:

试试这个

[self.messageArray removeAllObjects];
[self.messageArray addObject:[parsedData setObject:@"No Messages" forKey:@"getMessages"]];

大多数情况下字典没有设置键..只需检查..

还有,

NSDictionary *diction = [self.messageArray objectAtIndex:0];
NSString *string = [NSString stringWithFormat:@"%@", [diction objectForKey:@"getMessages"]]; 
if ([string isEqualToString:@"No Messages"])

    cell.textLabel.text = string;

else

    NSDictionary *dict = [self.messageArray objectAtIndex:indexPath.row];
    cell.textLabel.text = [NSString stringWithFormat:@"%@", [dict objectForKey:@"message"]];

【讨论】:

【参考方案2】:

首先确保 messageArray 被定义为 NSMutableArray... 如果您不时重新加载您的 parsedData,那么试试这个

if (![parsedData objectForKey:@"getMessages"])

    [self.messageArray removeAllObjects];
    [self.messageArray addObject:@"No Messages"];

else

    [self.messageArray removeAllObjects];
    self.messageArray = [[parsedData objectForKey:@"getMessages"] mutableCopy];

【讨论】:

以上是关于UITableView reloadData 崩溃并出现错误 [__NSCFConstantString objectForKey:]的主要内容,如果未能解决你的问题,请参考以下文章

UICollectionView 在 reloadData 后在屏幕外崩溃时崩溃

UITableView endUpdates 在 vi​​ewDidLoad 中调用时崩溃

在后台删除的数据导致 UITableView 中的索引超出范围崩溃

ReloadData (UITableView) 不起作用

为啥UITableView不能reloadData

关于UITableview刷新笔记