【问题标题】:Xcode UIImage imageWithCGImage leaks memoryXcode UIImage imageWithCGImage 内存泄漏
【发布时间】:2019-06-08 03:30:59
【问题描述】:

我在我的应用中启用了 ARC,并注意到如果我创建大量图像,我的应用会崩溃。作为调查的一部分,我创建了一个小项目来重现该问题,该问题可以在here 找到。示例项目代码的内容如下:

int width = 10;
int height = 10;
uint8_t data[100];

while (true)
{
    CGColorSpaceRef colorspace = CGColorSpaceCreateDeviceGray();
    CGContextRef context = CGBitmapContextCreate(data, width, height, 8, width, colorspace, kCGBitmapByteOrderDefault | kCGImageAlphaNone);
    CGImageRef cgimage = CGBitmapContextCreateImage(context);

    // Remove this line and memory is stable, keep it and you lose 15-20 MB per second. Why?
    UIImage* uiimage = [UIImage imageWithCGImage:cgimage];

    CGImageRelease(cgimage);
    CGContextRelease(context);
    CGColorSpaceRelease(colorspace);
}

运行此代码时,Xcode 中的侧边栏将显示应用程序的总内存以每秒 15-20 MB 左右的速度增加。如果您注释掉创建UIImage 的行,泄漏就会消失。

Stack Overflow 上有很多关于在通过imageWithCGImage 创建 UIImage 后是否应该发布CGImage 的问题,看起来并没有真正的共识。但是,如果我不调用CGImageRelease(cgimage),那么内存使用量每秒会增加超过 100 MB,所以我确信手动释放图像是正确的做法。

由于我启用了 ARC,我尝试在释放所有内容后将 uiimage 设置为 nil,但没有成功。不存储对imageWithCGImage: 的调用的返回值也不能防止泄漏。

关于如何使用 Core Graphics,我是否缺少一些基本知识?

【问题讨论】:

    标签: memory-leaks core-graphics


    【解决方案1】:

    关于如何使用 Core Graphics,我是否缺少一些基本知识?

    您似乎更有可能遗漏了一些关于内存管理的基本知识。

    许多 Foundation / Cocoa 框架命令,尤其是那些创建现成对象的命令,会生成自动释放的对象。这意味着您不必释放对象,因为它会在您完成后自动释放。但这怎么可能?这些对象进入自动释放池,一旦它们的保留计数下降到零,它们就会在以后有机会时被耗尽。但是你一直在循环,所以没有这样的机会。因此,您需要将麻烦的行包裹在 @autoreleasepool{} 块中,以便构建和耗尽您自己的池。

    另请注意,可能存在您不知道的中间自动释放对象。自动释放池也可以帮助解决这些问题。

    有关自动释放对象的更多信息,请参阅this section of my book

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 2013-10-26
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2014-07-02
      • 2011-08-31
      相关资源
      最近更新 更多