UITableView загружает миниатюры асинхронно с кешем

Я пытаюсь загрузить эскизы изображений с удаленного сайта в UITableView. Я хочу сделать это асинхронно, и я хочу реализовать кеш бедняка для миниатюрных изображений. Вот мой фрагмент кода (Я опишу проблемное поведение ниже):

@property (nonatomic, strong) NSMutableDictionary *thumbnailsCache;

- (UITableViewCell *)tableView:(UITableView *)tableView cellForRowAtIndexPath:(NSIndexPath *)indexPath

//...after obtaining the cell:

NSString *thumbnailCacheKey = [NSString stringWithFormat:@"cache%d", indexPath.row];

if (![[self.thumbnailsCache allKeys] containsObject:thumbnailCacheKey]) {

    // thumbnail for this row is not found in cache, so get it from remote website
    __block NSData *image = nil;        
    dispatch_queue_t imageQueue = dispatch_queue_create("queueForCellImage", NULL);
    dispatch_async(imageQueue, ^{
        NSString *thumbnailURL = myCustomFunctionGetThumbnailURL:indexPath.row;
        image = [[NSData alloc] initWithContentsOfURL:[NSURL URLWithString:thumbnailURL]];
        dispatch_async(dispatch_get_main_queue(), ^{
            cell.imageView.image = [UIImage imageWithData:image];
        });
    });
    dispatch_release(imageQueue);
    [self.thumbnailsCache setObject:image forKey:thumbnailCacheKey];

} else {

    // thumbnail is in cache
    NSData *image = [self.thumbnailsCache objectForKey:thumbnailCacheKey];
    dispatch_async(dispatch_get_main_queue(), ^{
        cell.imageView.image = [UIImage imageWithData:image];
    });

}

Итак, вот проблемное поведение:

  1. Когда загружается UITableView, эскизы не отображаются в начальном наборе ячеек. Миниатюра отображается только тогда, когда ячейка перемещается за пределы экрана, а затем возвращается обратно.

  2. Кэш вообще не работает. Из того, что я могу сказать, он не может вообще сохранить миниатюру в кэш. То есть эта строка не работает:

    [self.thumbnailsCache setObject:изображение для ключа:thumbnailCacheKey];

  3. Очередь GCD создается/освобождается для каждой ячейки. Кроме того, имя очереди всегда одно и то же. Это плохая практика?

Ребята, я был бы признателен, если бы вы указали на все, что вы видите неправильно, или даже на любые комментарии общего подхода. Спасибо.

Обновление:

  1. RESOLVED:Я добавил вызов reloadRowsAtIndexPaths, и теперь миниатюры загружаются в начальных строках, которые отображают

  2. RESOLVED:Причина сбоя в том, что он добавлял объект изображения в словарь до того, как другой поток завершит настройку этого объекта. Я создал метод экземпляра для добавления объекта в словарь свойств, чтобы я мог вызывать его из блока, гарантируя, что он будет добавлен после установки объекта изображения.

5
задан Steven 14 April 2012 в 23:38
поделиться