主要問題
- 同步請求阻塞 UI:
sendSynchronousRequest 在主執行緒執行,會凍結介面,甚至觸發 Watchdog 殺掉 App。
- cell 配置順序錯誤:
cellForRowAtIndexPath 中 return cell; 放在設定文字**之前**,導致後續代碼不執行。
修正代碼
- (void)loadData {
NSURL *url = [NSURL URLWithString:@"https://api.example.com/data"];
NSURLSessionDataTask *task = [[NSURLSession sharedSession] dataTaskWithURL:url completionHandler:^(NSData *data, NSURLResponse *response, NSError *error) {
if (error) { NSLog(@"Error: %@", error); return; }
NSError *jsonError;
NSArray *jsonArray = [NSJSONSerialization JSONObjectWithData:data options:0 error:&jsonError];
if (jsonError) { NSLog(@"JSON Error: %@", jsonError); return; }
dispatch_async(dispatch_get_main_queue(), ^{
self.statuses = jsonArray; // 保存模型陣列
[self.dropdownTblView reloadData];
});
}];
[task resume];
}
- (UITableViewCell *)tableView:(UITableView *)tableView cellForRowAtIndexPath:(NSIndexPath *)indexPath {
static NSString *CellID = @"Cell";
UITableViewCell *cell = [tableView dequeueReusableCellWithIdentifier:CellID];
if (!cell) {
cell = [[UITableViewCell alloc] initWithStyle:UITableViewCellStyleDefault reuseIdentifier:CellID];
}
// 先取模型,再配置,最後 return
NSDictionary *item = self.statuses[indexPath.row];
cell.textLabel.text = item[@"Title"];
return cell; // 正確位置
}
關鍵改進
- 改用
NSURLSession 非同步請求,回調在背景隊列,UI 更新切回主隊列。
- 模型資料儲存為陣列屬性
self.statuses,而非臨時變數。
cellForRowAtIndexPath 邏輯線性化:dequeue → configure → return。
進階建議
- 使用
SDWebImage / Kingfisher 非同步載入圖片(若 JSON 含圖片 URL)。
- 採用
Codable (Swift) 或 MJExtension (OC) 自動映射模型。
- 大量資料考慮分頁載入與
UITableViewDataSourcePrefetching。