在从JSON解析对象之后,我试图填充一个表视图。我希望将行数设置为已解析对象的计数。
这是我的viewDidLoad代码:
- (void)viewDidLoad
{
[super viewDidLoad];
// initializing data source
[self setNotifications:[[NSMutableArray alloc] init]];
NSURL *url = [NSURL URLWithString:SourceURL];
NSURLRequest *request = [NSURLRequest requestWithURL:url];
AFJSONRequestOperation *operation = [AFJSONRequestOperation JSONRequestOperationWithRequest:request success:^(NSURLRequest *request, NSHTTPURLResponse *response, id JSON) {
[self setNotifications:[JSON objectForKey:@"notifications"]];
// [[self tableView] setHidden:NO];
[[self tableView] reloadData];
} failure:^(NSURLRequest *request, NSHTTPURLResponse *response, NSError *error, id JSON) {
NSLog(@"Request Failure Because %@",[error userInfo]);
}];
[operation start];}
以下是我的数据源方法之一(我认为错误肯定在这里):
- (NSInteger)tableView:(UITableView *)tableView numberOfRowsInSection:(NSInteger)section
{
if ([self notifications] && [[self notifications] count] ) {
return [[self notifications] count];
} else{
return 0;
}
}以下是我的完整错误信息:
> *** Terminating app due to uncaught exception 'NSRangeException', reason: '*** -[__NSArrayI objectAtIndex:]: index 1 beyond bounds [0 ..
> 0]'
> *** First throw call stack: (0x13c4012 0x118ce7e 0x1379b44 0x510c04 0x300ea0 0x2b5c4e 0x2b8224 0x17c952 0x17c2dc 0xc4a9d14 0x26e0 0x16ea2
> 0x18409 0x162753f 0x1639014 0x16297d5 0x136aaf5 0x1369f44 0x1369e1b
> 0x22647e3 0x2264668 0xd0ffc 0x1f1d 0x1e45) libc++abi.dylib: terminate
> called throwing an exception更新
下面是我的cellForRowAtIndexpath方法:
- (UITableViewCell *)tableView:(UITableView *)tableView cellForRowAtIndexPath:(NSIndexPath *)indexPath
{
static NSString *cellID = @"readNotification";
UITableViewCell *cell = [tableView dequeueReusableCellWithIdentifier:cellID];
if (!cell){
cell = [[UITableViewCell alloc] initWithStyle:UITableViewCellStyleSubtitle reuseIdentifier:cellID];
}
NSDictionary *notification = [[self notifications] objectAtIndex:[indexPath row]];
[[cell textLabel] setText:[notification objectForKey:@"from"]];
[[cell detailTextLabel] setText:[notification objectForKey:@"date"]];
return cell;
}更新2
我向项目添加了一些日志,它提供了一些有趣的输出:
2013-08-06 23:53:53:03.994 NotificationReader1193:c07 1.在请求前-2013年-08-06 23:53:04.023 NotificationReader1193:53:04.319 NotificationReader1193: json parshing操作开始于2013-08-06 23:53:04.031 NotificationReader1193:c07。进入numberOfRowsInSection块201-08-06 23:53:04.040 NotificationReader1193:c07没有通知2013-08-06 23:53:04.319 NotificationReader1193:c07进入numberOfRowsInSection块2013-08-06 23:53:04.320 NotificationReader1193:c07。2013-08-06 14份通知23:53:08.260 NotificationReader1193 1193:C07*终止应用程序
因此,首先它认为我的数组是空的,然后它重新加载并获得正确的通知计数。不幸的是,它从未进入cellForRowAtIndexPath方法。
更新3
我在我的项目中添加了一个异常断点,加上一些额外的日志记录,我假设它在重新加载表视图时遇到了问题。以下是到目前为止的结果:
2013-08-07 08:40:58.104 NotificationReader[433:c07] 1. before request
2013-08-07 08:40:58.107 NotificationReader[433:c07] 2. json parshing operation started
2013-08-07 08:40:58.113 NotificationReader[433:c07] 3. entered the numberOfRowsInSection block
2013-08-07 08:40:58.120 NotificationReader[433:c07] Found 0 notifications!
2013-08-07 08:41:10.852 NotificationReader[433:c07] Trying to reload data
2013-08-07 08:41:10.853 NotificationReader[433:c07] data needs to be reloaded
2013-08-07 08:41:10.854 NotificationReader[433:c07] 3. entered the numberOfRowsInSection block
2013-08-07 08:41:10.855 NotificationReader[433:c07] Found 14 notifications!
2013-08-07 08:41:10.858 NotificationReader[433:c07] *** Terminating app due to uncaught exception 'NSRangeException', reason: '*** -[__NSArrayI objectAtIndex:]: index 1 beyond bounds [0 .. 0]'
*** First throw call stack:
(0x13c5012 0x118de7e 0x137ab44 0x511c04 0x301ea0 0x2b6c4e 0x2b9224 0x17d952 0x17d2dc 0xc4c0d14 0x351b 0x162853f 0x163a014 0x162a7d5 0x136baf5 0x136af44 0x136ae1b 0x22657e3 0x2265668 0xd1ffc 0x2c4d 0x2b75)
libc++abi.dylib: terminate called throwing an exception}堆栈跟踪:
#0 0x0118de52 in objc_exception_throw ()
#1 0x0137ab44 in -[__NSArrayI objectAtIndex:] ()
#2 0x00511c04 in -[UITableViewDataSource tableView:heightForRowAtIndexPath:] ()
#3 0x00301ea0 in -[UITableViewController tableView:heightForRowAtIndexPath:] ()
#4 0x002b6c4e in -[UISectionRowData refreshWithSection:tableView:tableViewRowData:] ()
#5 0x002b9224 in -[UITableViewRowData numberOfRows] ()
#6 0x0017d952 in -[UITableView noteNumberOfRowsChanged] ()
#7 0x0017d2dc in -[UITableView reloadData] ()
#8 0x0c4a9d14 in -[UITableViewAccessibility(Accessibility) reloadData] ()
#9 0x0000351b in __36-[NRTableViewController viewDidLoad]_block_invoke_2 at /Users/jozsef/Development/NotificationReader/NotificationReader/NRTableViewController.m:52我尝试使用lldb,结果如下:
(lldb) po [[self notifications] count]
error: Execution was interrupted, reason: Attempted to dereference an invalid pointer..
The process has been returned to the state before execution.发布于 2013-08-06 22:56:08
这是由于试图访问超出数组界限的索引造成的。从外观来看,唯一的数组访问是在-tableView:cellForRowAtIndexPath:中。
NSDictionary *notification = [[self notifications] objectAtIndex:[indexPath row]];我希望这就是出现例外情况的地方。
您可以通过添加“添加异常断点.”来确定。从断点导航器。
通过确认[indexPath row]在[self notifications]数组的范围内来修正这个问题。或者,如果您认为这应该总是在范围内,那么就找出它为什么会超出界限。
另外,您可以重写一个方法,如下所示:
- (NSInteger)tableView:(UITableView *)tableView numberOfRowsInSection:(NSInteger)section
{
return [self.notifications count];
}如果self.notifications为零,则返回0。如果计数为0,则显然将返回0。所以这就是我们所需要的。
编辑:最后,您还可以使用订阅重写数组访问,如下所示:
NSDictionary *notification = self.notifications[indexPath.row];确保调用AFJSONRequestOperation成功块中主线程上的UI更新,即
AFJSONRequestOperation *operation = [AFJSONRequestOperation JSONRequestOperationWithRequest:request success:^(NSURLRequest *request, NSHTTPURLResponse *response, id JSON) {
// update on the main thread!
dispatch_async(dispatch_get_main_queue(), ^{
[self setNotifications:[JSON objectForKey:@"notifications"]];
// [[self tableView] setHidden:NO];
[[self tableView] reloadData];
});
} failure:^(NSURLRequest *request, NSHTTPURLResponse *response, NSError *error, id JSON) {
NSLog(@"Request Failure Because %@",[error userInfo]);
}];发布于 2013-08-06 21:31:59
批注是正确的,您应该通过设置断点和遍历代码来调试这类事情。用日志语句来补充这种方法。
您还应该在Xcode中设置一个“所有异常断点”(命令-6,然后按左下角的+按钮)。
此错误可能不会发生在numberOfRowsInSection中。它可能发生在cellForRowAtIndexPath中吗?
NSDictionary *notification = [[self notifications] objectAtIndex:[indexPath row]];
正如您在nil和count中签入numberOfRowsInSection一样,您在这里也应该这样做:
if (self.notifications) {
if (indexPath.row < [self.notifications count]) {
NSDictionary *notification = [[self notifications] objectAtIndex:[indexPath row]];`
//...
}
}我的猜测是,JSON响应不是您预期的那样,因此self.notifications不是您所期望的那样。
发布于 2013-08-07 11:08:40
在不同的机器上运行代码之后,所有的代码似乎都能正常工作。在我的配置中肯定有一些垃圾,所以我再次添加了该项目,并可以确认它正在工作。山姆,特别感谢你的考验和耐心!
https://stackoverflow.com/questions/18090424
复制相似问题