Выпустите CGImageRef, чтобы избежать утечки памяти

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

скриншот кода

Я пытался сделать CFRelease(rawImageRef); но возвращает следующую ошибку:

-[Not A Type retain]: message sent to deallocated instance 0x14dd3770

Обновление с кодом:

- (CGColorRef)averageColorRect:(CGRect)rect {

    CGImageRef rawImageRef = CGImageCreateWithImageInRect(_imageRaster, rect);

    // This function returns the raw pixel values
    CFDataRef data = CGDataProviderCopyData(CGImageGetDataProvider(rawImageRef));
    const UInt8 *rawPixelData = CFDataGetBytePtr(data);

    NSUInteger imageHeight = CGImageGetHeight(rawImageRef);
    NSUInteger imageWidth  = CGImageGetWidth(rawImageRef);
    NSUInteger bytesPerRow = CGImageGetBytesPerRow(rawImageRef);
    NSUInteger stride = CGImageGetBitsPerPixel(rawImageRef) / 8;

    // Here I sort the R,G,B, values and get the average over the whole image
    unsigned int red   = 0;
    unsigned int green = 0;
    unsigned int blue  = 0;

    for (int row = 0; row < imageHeight; row++) {
        const UInt8 *rowPtr = rawPixelData + bytesPerRow * row;
        for (int column = 0; column < imageWidth; column++) {
            red    += rowPtr[0];
            green  += rowPtr[1];
            blue   += rowPtr[2];
            rowPtr += stride;

        }
    }
    CFRelease(data);

    CGFloat f = 1.0f / (255.0f * imageWidth * imageHeight);
    return [UIColor colorWithRed:f * red  green:f * green blue:f * blue alpha:1].CGColor;

}

3 ответа

Вы никогда не выпускаете rawImageRef,

Я бы позвонил CGImageRelease(rawImageRef); сразу после выпуска data,

Да, статический анализатор правильный, то что тебе нужно CGImageRelease(rawImageRef) в рамках этого метода.

Однако ваша ошибка сообщает о чрезмерном выпуске какого-либо объекта. На основании предоставленного фрагмента кода, я не думаю, что rawImageRef это рассматриваемый объект.

Теперь я не знаю, что вы делаете с возвращенными CGColorRef объект, но скажем, у вас было что-то вроде следующего:

CGColor colorRef = [self averageColorRect:CGRectMake(0, 0, 20, 20)];

// do something with `colorRef`

// now, all done, clean up

CGColorRelease(colorRef);        // error; you don't want this line

Если у вас включены зомби, это приводит к ошибке, которую вы описываете:

- [Not A Type release]: сообщение отправлено освобожденному экземпляру 0x8de4e90

Это потому что colorRef объект, который вы возвращаете, связан с автоматическим выпуском UIColor объект, и, следовательно, когда бассейн осушается, CGColorRef объект будет освобожден, если вы не сделали явное CGColorRetain, В этом случае эта ошибка исчезнет, ​​если вы удалите ненужные CGColorRelease,

Я не предполагаю, что это именно то, что вы сделали, но это иллюстрация того, что может вызвать ошибку, о которой вы сообщаете. Возможно, вы можете поделиться своим кодом, который использует полученный CGColorRef и мы можем увидеть, есть ли что-нибудь, что могло бы показать ошибку, которой вы поделились с нами. Непонятно, почему введение CGImageRelease(rawImageRef) приведет к появлению этой ошибки, в то время как она не возникает в отсутствие этого CGImageRelease, Но CGImageRelease(rawImageRef) это не корень проблемы, а вопрос, несомненно, лежит в другом месте.

Решено! Я добавил _imageRaster.CGIMage и после релиза!! Спасибо!

CGImageRef rawImageRef = CGImageCreateWithImageInRect(_imageRaster.CGImage, rect);

// ......

CGImageRelease(rawImageRef);
Другие вопросы по тегам