在内存限制下调整UIImage的大小

我从Web资源(> 300MB)下载了大量的UIImage,当我尝试渲染时,由于内存导致应用程序崩溃。 我正在尝试使用以下代码调整图像大小:

+ (UIImage *)imageWithImage:(UIImage *)image scaled:(float) scale { //UIGraphicsBeginImageContext(newSize); CGSize size = (CGSize){scale * image.size.width, scale * image.size.height}; UIGraphicsBeginImageContextWithOptions(size, NO, 0.0); [image drawInRect:CGRectMake(0, 0, size.width, size.height)]; UIImage *newImage = UIGraphicsGetImageFromCurrentImageContext(); UIGraphicsEndImageContext(); return newImage; } 

问题是,正如您可能已经猜到的那样,这需要实际渲染图像,从而导致同样的崩溃。 有没有办法在不给系统带来如此巨大的内存压力的情况下调整大图像的大小?

问题是你将图像保存在内存中。 将其下载到磁盘并使用ImageIO框架直接从磁盘读取“缩略图”(较小的大小),而无需在内存中保存全尺寸图像。

您可以尝试这个+ (UIImage *)decodedImageWithImage:(UIImage *)image maxSize:(NSInteger) maxSize. 来自SDWebImage代码

 #define MAX_IMAGE_SIZE 1000 @implementation UIImage (ForceDecode) + (CGSize) originalSize:(UIImage*) image { return CGSizeMake(CGImageGetWidth(image.CGImage), CGImageGetHeight(image.CGImage)); } + (UIImage *)decodedImageWithImage:(UIImage *)image { return [self decodedImageWithImage:image maxSize:MAX_IMAGE_SIZE]; } + (UIImage *)decodedImageWithImage:(UIImage *)image maxSize:(NSInteger) maxSize{ if (image.images) { // Do not decode animated images return image; } CGImageRef imageRef = image.CGImage; CGSize imageSize = CGSizeMake(CGImageGetWidth(imageRef), CGImageGetHeight(imageRef)); imageSize = [self checkMaxImageSize:imageSize maxSize:maxSize]; CGRect imageRect = (CGRect){.origin = CGPointZero, .size = imageSize}; CGColorSpaceRef colorSpace = CGColorSpaceCreateDeviceRGB(); CGBitmapInfo bitmapInfo = CGImageGetBitmapInfo(imageRef); int infoMask = (bitmapInfo & kCGBitmapAlphaInfoMask); BOOL anyNonAlpha = (infoMask == kCGImageAlphaNone || infoMask == kCGImageAlphaNoneSkipFirst || infoMask == kCGImageAlphaNoneSkipLast); // CGBitmapContextCreate doesn't support kCGImageAlphaNone with RGB. // https://developer.apple.com/library/mac/#qa/qa1037/_index.html if (infoMask == kCGImageAlphaNone && CGColorSpaceGetNumberOfComponents(colorSpace) > 1) { // Unset the old alpha info. bitmapInfo &= ~kCGBitmapAlphaInfoMask; // Set noneSkipFirst. bitmapInfo |= kCGImageAlphaNoneSkipFirst; } // Some PNGs tell us they have alpha but only 3 components. Odd. else if (!anyNonAlpha && CGColorSpaceGetNumberOfComponents(colorSpace) == 3) { // Unset the old alpha info. bitmapInfo &= ~kCGBitmapAlphaInfoMask; bitmapInfo |= kCGImageAlphaPremultipliedFirst; } // It calculates the bytes-per-row based on the bitsPerComponent and width arguments. CGContextRef context = CGBitmapContextCreate(NULL, imageSize.width, imageSize.height, CGImageGetBitsPerComponent(imageRef), 0, colorSpace, bitmapInfo); CGColorSpaceRelease(colorSpace); // If failed, return undecompressed image if (!context) return image; CGContextDrawImage(context, imageRect, imageRef); CGImageRef decompressedImageRef = CGBitmapContextCreateImage(context); CGContextRelease(context); UIImage *decompressedImage = [UIImage imageWithCGImage:decompressedImageRef scale:image.scale orientation:image.imageOrientation]; CGImageRelease(decompressedImageRef); return decompressedImage; } + (CGSize) checkMaxImageSize:(CGSize) size maxSize:(NSInteger) max { CGFloat whRatio = size.width / size.height; if (size.height > max || size.width > max) { if (size.height > size.width) { size.width = max * whRatio; size.height = max; }else{ size.width = max ; size.height = max / whRatio; } } return size; }