【问题标题】:Downloading 1000 images asynchronously and doing caching but its giving memory issue异步下载 1000 张图像并进行缓存,但存在内存问题
【发布时间】:2016-04-02 06:43:39
【问题描述】:

我有一个代码可以下载大约 1000 张图像,还可以使用 NSCache 执行缓存并在 UICollectionView 中显示图像。它可以工作,但是当 UICollectionView 滚动得非常快并且互联网速度很慢时,会收到内存警告。那么这里的问题可能是什么?以下是我的代码:提前致谢。

- (UICollectionViewCell *)collectionView:(UICollectionView *)collectionView cellForItemAtIndexPath:(NSIndexPath *)indexPath {
      ProductCollectionViewCell *cell = (ProductCollectionViewCell *)[collectionView dequeueReusableCellWithReuseIdentifier:identifier forIndexPath:indexPath];

      //set image,title of product
      cell.productLabel.text = [self.productNameArray objectAtIndex:indexPath.row];
      UIImage *image = [self.imgCache getCachedImageForKey:[self.imgUrlArray objectAtIndex:indexPath.row]];
      if (image.size.width>0) {
        [cell.productImage setImage:image];
      }
      else {
        [cell.productImage setImage:nil];
    dispatch_async(dispatch_get_global_queue(DISPATCH_QUEUE_PRIORITY_HIGH, 0), ^(void){
        NSData *imgData = [NSData dataWithContentsOfURL:[NSURL URLWithString:[self.imgUrlArray objectAtIndex:indexPath.row]]];
        UIImage *img = [UIImage imageWithData:imgData];
        [cell.productImage setImage:nil];
        dispatch_async(dispatch_get_main_queue(), ^{
            if (imgData!=nil) {
                [cell.productImage setImage:img];
                [self.imgCache cacheImage:img forKey:[self.imgUrlArray objectAtIndex:indexPath.row]];
                if ([self.imgDataArray count] <= [self.productNameArray count]) {
                    [self.imgDataArray addObject:imgData];
                }
            }
        });
        if ([self.imgDataArray count] == [self.productNameArray count]){
            [self.productsView.collectionView reloadData];
        }
    });    
}
return cell;
}

【问题讨论】:

    标签: ios objective-c uicollectionview


    【解决方案1】:

    你可以用这个SDWebImage

    [cell.imageView sd_setImageWithURL:[NSURL URLWithString:@"http://www.domain.com/path/to/image.jpg"]
                          placeholderImage:[UIImage imageNamed:@"placeholder.png"]];
    

    【讨论】:

      【解决方案2】:

      尝试制作 UIImageView 类别文件以从 url 下载图像,它将文件保存在设备的缓存中,当您想再次加载该图像时,它将从缓存中加载该图像。这是我的代码链接Dowinload Image and store in the cache using category

      【讨论】:

        【解决方案3】:

        使用SDWebImage 框架。 以下是链接或如何将其与项目链接: https://github.com/rs/SDWebImage

        下面是如何使用SDWebImage下载图片的代码。

        [cell.itemimage sd_setImageWithURL:[NSURL URLWithString:URLString] placeholderImage:[UIImage imageNamed:@"loadingImage"] options:SDWebImageRefreshCached completed:^(UIImage *image, NSError *error, SDImageCacheType cacheType, NSURL *imageURL) {
            cell.itemimage.image = image;
            dispatch_async(dispatch_get_main_queue(), ^{
                [cell setNeedsDisplay];
            });
        }];
        

        【讨论】:

          【解决方案4】:

          从 url 获取数据并在 cellForItemAtIndexPath 中调用 imageWithData 似乎并不好。虽然图像没有被缓存,但它会在每次调用单元格时尝试获取数据,这不是建议的方法。在外部函数中获取图像数据并仅重新加载表格视图或相应的行。

          试试这样的

          - (void)downloadImages {
              for (int i = 0; i < self.imgUrlArray.count; i++) {
                  dispatch_async(dispatch_get_global_queue(DISPATCH_QUEUE_PRIORITY_HIGH, 0), ^(void){
                      NSData *imgData = [NSData dataWithContentsOfURL:[NSURL URLWithString:[self.imgUrlArray objectAtIndex:i]]];
          
                      if(imgData) {
                          UIImage *img = [UIImage imageWithData:imgData];
          
                          if(img) {
                              // Cache image
                              dispatch_async(dispatch_get_main_queue(), ^{
                                  // reload collection view
                              });
                          }
                      }
                  });
              }
          }
          

          所以在你的 cellForItemAtIndexPath 方法中你只需要这样做

          if (image) {
                  [cell.productImage setImage:image];
                }
                else {
          [cell.productImage setImage:nil];
          }
          

          【讨论】:

            猜你喜欢
            • 2017-12-24
            • 1970-01-01
            • 1970-01-01
            • 2011-07-01
            • 1970-01-01
            • 2020-05-25
            • 1970-01-01
            • 1970-01-01
            • 1970-01-01
            相关资源
            最近更新 更多