[英]NSOperationQueue and UITableView
我正在從SQLite數據庫加載一些數據,以顯示在UITableView
。 為了確保用戶沒有被阻塞並且表可以快速顯示,我創建了一個隊列並添加了要在后台執行的數據庫操作。
添加是好的並且可以正常工作,但是由於某些原因,某些行不會隨數據一起更新!
我知道數據設置正確,因為當我單擊該行時,該行將用我的數據進行更新,但是我似乎找不到更新UI的方法! 我已經嘗試了一切,包括使用setNeedDisplay
等,但是沒有任何效果!
這是我的代碼:
- (UITableViewCell *) tableView:(UITableView *)tableView cellForRowAtIndexPath:(NSIndexPath *)indexPath{
static NSString *CellIdentifier = @"Cell";
UITableViewCell* cell = (UITableViewCell*)[tableView dequeueReusableCellWithIdentifier:CellIdentifier];
if (cell == nil) {
cell = [[[UITableViewCell alloc] initWithStyle:UITableViewCellStyleDefault reuseIdentifier:CellIdentifier] autorelease];
cell.textLabel.textAlignment = UITextAlignmentRight;
cell.textLabel.numberOfLines = 0;
cell.textLabel.font = [UIFont systemFontOfSize:14];
}
cell.accessoryType = UITableViewCellAccessoryNone;
cell.textLabel.text = @"Loading ...";
cell.tag = indexPath.row;
NSInvocationOperation *op = [[NSInvocationOperation alloc] initWithTarget:self
selector:@selector(setCellData:)
object:cell];
[queue addOperation:op];
[op release];
return cell;
}
- (void) setCellData:(UITableViewCell *)cell{
NSAutoreleasePool *pool = [[NSAutoreleasePool alloc] init];
sqlite3_stmt *statement2;
NSString *sqlStr = [NSString stringWithFormat:@"SELECT * FROM poemdata WHERE catid='%d' GROUP BY poemid LIMIT 1 OFFSET %d",catId,cell.tag];
// NSLog(@"%@",sqlStr);
sqlite3_prepare_v2(database, [sqlStr cStringUsingEncoding:NSASCIIStringEncoding], -1, &statement2, nil);
cell.accessoryType = UITableViewCellAccessoryDisclosureIndicator;
if(sqlite3_step(statement2) == SQLITE_ROW){
cell.textLabel.text = [[NSString alloc] initWithUTF8String: (char *)sqlite3_column_text(statement2, 3)];
cell.tag = sqlite3_column_int(statement2, 6);
}else{
cell.textLabel.text = @"Error";
}
sqlite3_finalize(statement2);
[pool release];
}
您的邏輯有缺陷,我認為您將體驗到糟糕的性能以及已經遇到的問題。 最好啟動整體操作以加載所有數據或至少部分數據,然后要求表完成時重新加載。
現在,您的操作方式是每個單元都在訪問數據庫並選擇一行,而不在任何地方緩存該數據(這意味着如果它滾動到視圖外然后再次返回,則必須再次訪問數據庫)。 另外,操作完成時,此單元格上沒有調用繪制代碼(這就是為什么直到單擊它會引起繪制調用后它才會顯示的原因)。
您應該將所有這些數據加載到自定義對象的數組中。 加載后,您應該重新加載表並使用新填充的數組在單元格中設置屬性。
您正在從后台線程更新用戶界面,這是錯誤的。 所有用戶界面工作必須在主線程上完成。 嘗試將與cell
所有交互都移到主線程,將數據從后台線程傳遞到NSDictionary
。
請參見performSelectorOnMainThread:withObject:waitUntilDone:。 另請參閱《 Apple線程編程指南》中的“ 線程和用戶界面 ”。
@theChrisKent很好地說明了性能,盡管此線程問題很可能是您行為失常的原因。
聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.