今天開發(fā) 崩潰 報錯:
[UITableView _contentOffsetForScrollingToRowAtIndexPath:atScrollPosition:]:row (x) beyond bounds...
原因:
執(zhí)行
[UITableView reloadDate]
或者其他刷新 UITableView 的方法;
Cell 計算量 數(shù)據(jù)量比較大的情況下,在一個run loop周期沒執(zhí)行完乔夯;
UITableView 會可能在數(shù)據(jù)還沒加載完就立即去執(zhí)行
數(shù)據(jù)源-(NSInteger)tableView:(UITableView *)tableView numberOfRowsInSection:(NSInteger)section方法蒂培。
可能會有崩潰情況。
解決方法:
邏輯:把數(shù)據(jù)加載放回主線程,先保證數(shù)據(jù)加載完整了再執(zhí)行數(shù)據(jù)源的代理方法烧颖。
方法一:
等待線程完成
//1.先讓 reloadDate 在主隊列執(zhí)行
[tableView reloadData];
//2.dispatch_get_main_queue會等待機(jī)會,直到主隊列空閑窄陡,也就是數(shù)據(jù)加載完畢才繼續(xù)執(zhí)行炕淮。
dispatch_async(dispatch_get_main_queue(), ^{
//刷新完成 / 各種操作
//我之前崩潰就是這個刷新 會有崩潰 置入 這里就沒有崩潰情況
[tableView reloadSections:[[NSIndexSet alloc] initWithIndex:section] withRowAnimation:UITableViewRowAnimationAutomatic];
});
方法二:
進(jìn)行重繪
[tableView reloadData];
// 強(qiáng)制重繪并等待完成
[tableView layoutIfNeeded];
//我之前崩潰就是這個刷新 會有崩潰 置入 這里就沒有崩潰情況
[tableView reloadSections:[[NSIndexSet alloc] initWithIndex:section] withRowAnimation:UITableViewRowAnimationAutomatic];
推薦!(新增)方法三:
邏輯:判斷 UITableView 是否加載完成(是否存在), 完成后再繼續(xù)下一步
-(void) tableView:(UITableView *)tableView willDisplayCell:(UITableViewCell *)cell forRowAtIndexPath:(NSIndexPath )indexPath
{
//用于判斷tableview當(dāng)前是否加載完成
if([indexPath row] == ((NSIndexPath)[[_mainTableView indexPathsForVisibleRows] lastObject]).row){
//加載已結(jié)束 表示已存在
dispatch_async(dispatch_get_main_queue(),^{
//dispatch_get_main_queue會等待機(jī)會跳夭,直到主隊列空閑涂圆,也就是數(shù)據(jù)加載完畢才繼續(xù)執(zhí)行。
[tableView scrollToRowAtIndexPath:indexPath atScrollPosition:UITableViewScrollPositionMiddle animated:YES];
/*
刷新 币叹、定位 等操作 可以置入這里润歉。
也可以提取方法到外面去,會靈活點(diǎn)套硼。
這個主要是判斷存在與否 [indexPath row] == ((NSIndexPath*)[[tableView indexPathsForVisibleRows] lastObject]).row
*/
});
}
}
以上三個方法卡辰,個人推薦第三個方法。