Objectice-C之关联对象

 static NSString *CellIdentifier = @"Cell";
    
    //重用单元格
    JKCallbacksTableViewCell *cell = (JKCallbacksTableViewCell *)[tableView dequeueReusableCellWithIdentifier:CellIdentifier];
    if (cell == nil) {
        cell = [[[JKCallbacksTableViewCell alloc] initWithStyle:UITableViewCellStyleDefault
                                                reuseIdentifier:CellIdentifier] autorelease];
    }
    
    //获得要加载的文件名
    NSString *imageFilename = [imageArray objectAtIndex:[indexPath row]];
    NSString *imagePath = [imageFolder stringByAppendingPathComponent:imageFilename];
    
    //图片名称
    [[cell textLabel] setText:imageFilename];
    [cell setSelectionStyle:UITableViewCellSelectionStyleNone];
    
    // If we already have an image cached for the cell, use that. Otherwise we need to go into the 
    // background and generate it.
    UIImage *image = [imageCache objectForKey:imageFilename];
    if (image) {
        //图片缓存不存在,加载图片
        [[cell imageView] setImage:image];
    } else {    
        dispatch_queue_t queue = dispatch_get_global_queue(DISPATCH_QUEUE_PRIORITY_DEFAULT, 0ul);
        
        // Get the height of the cell to pass to the block.
        CGFloat cellHeight = [tableView rowHeight];
        
        // Now, we can’t cancel a block once it begins, so we’ll use associated objects and compare
        // index paths to see if we should continue once we have a resized image.
        // 创建关联对象
        /**
         * @param cell                          源对象
         * @param kIndexPathAssociationKey      关联key
         * @param indexPath                     关联的值
         * @param OBJC_ASSOCIATION_RETAIN       关联方式
         */
        objc_setAssociatedObject(cell,
                                 kIndexPathAssociationKey,
                                 indexPath,
                                 OBJC_ASSOCIATION_RETAIN);
        
        /*
         使用关联引用,你可以对一个对象添加数据而不需要修改这个类定义,这在你没有这个类的源代码时很有用,
         或者是为了二进制兼容的原因你无法修改这个对象的时候。
         
         关联基于一个key,所以你可以在一个对象上添加多个关联,每个使用不同的key,关联对象也可以确保被关
         联的对象是否存在,至少在源对象的生命周期内(也就是说这个对象没有将被引入到垃圾回收系统的可能性)
         */
        
        dispatch_async(queue, ^{
            //子线程
            UIImage *image = [UIImage imageWithContentsOfFile:imagePath];
            
            //调整图片大小
            UIImage *resizedImage = [image resizedImageWithContentMode:UIViewContentModeScaleAspectFill
                                                                bounds:CGSizeMake(cellHeight, cellHeight)
                                                  interpolationQuality:kCGInterpolationHigh];
            
            dispatch_async(dispatch_get_main_queue(), ^{
                //主线程(异步操作)
                
                //检索关联对象
                NSIndexPath *cellIndexPath =
                (NSIndexPath *)objc_getAssociatedObject(cell, kIndexPathAssociationKey);
                
                if ([indexPath isEqual:cellIndexPath]) {
                    [[cell imageView] setImage:resizedImage];
                }
                //根据文件名来作为缓存的key
                [imageCache setObject:resizedImage forKey:imageFilename];
            });
        });
    }
posted @ 2012-09-08 14:28  FoxBabe  阅读(515)  评论(1编辑  收藏  举报