使用ARC进行内存分配 - 没有泄漏但缓慢堆积内存

时间:2015-07-12 21:05:23

标签: ios objective-c xcode memory-management automatic-ref-counting

我已经开始编写我的第一次认真尝试用于iOS的混合Cordova / Objective-C程序,而且我目前正在尝试关于内存分配的一些绊脚石。我需要让用户的相册艺术在网页视图中显示。我得到了成功展示的艺术,但现在已经分配了大量的内存。

使用"仪器"工具和比较代际快照,我已经将我的罪魁祸首缩小到这些方法 - 我从头开始写这些方法。但我很困惑 - 因为我使用自动引用计数,并且我拥有自动释放池中的所有内容,因此不应该浪费任何内存。有趣的是,我看不到"泄漏"被报告 - 只是一个变大的堆,分配的内存越来越多。

我附上了乐器工具的一些截图:

以下是图片的直接链接,因为文字太多了:

http://i.imgur.com/rkc5dhA.png

http://i.imgur.com/U2esgBT.png

http://i.imgur.com/fmt3Mv4.png

这里是" BukketHelper.M"的内容。我创建的类(匹配标题,没有强大的属性或任何其他任何类型的定义):

-(NSString *)   convertULLToNSString:(NSNumber* )guid
{
    return [NSString stringWithFormat:@"%llu", [guid unsignedLongLongValue]];
}

-(NSNumber *)   convertStringToULL:(NSString *) guid
{
    //get string to number
    //this causes memory to not be released
    unsigned long long ullvalue = strtoull([guid UTF8String], NULL, 10);
    NSNumber *numberID = [[NSNumber alloc] initWithUnsignedLongLong:ullvalue];

    return numberID;
}

这是" MediaQuery.M"的内容。我创建的类(这与标题完全匹配,没有强大的属性或其他定义):

-(MPMediaItem*) getMediaItemULL:(NSNumber*)guid
{
    @autoreleasepool {
         //run the query on
        MPMediaQuery *query = [[MPMediaQuery alloc] init];
        [query addFilterPredicate:[MPMediaPropertyPredicate predicateWithValue:guid forProperty:MPMediaItemPropertyPersistentID]];

        //get and return the item
        NSArray *mediaResults = [query items];
        return [mediaResults firstObject];
    }
}

-(MPMediaItem*) getMediaItem:(NSString*)guid
{
    @autoreleasepool {
        BukketHelper* bh = [[BukketHelper alloc] init];
        return [self getMediaItemULL:[bh convertStringToULL:guid]];
    }
}

-(UIImage*) getMediaAlbumArtAsUIImage:(NSString*)guid withQuality:(NSNumber*)quality withLength:(NSNumber*)length subsituteImageName:(NSString* )filename
{
    return [self getMediaAlbumArtFromMediaItemAsUIImage:[self getMediaItem:guid] withQuality:quality withLength:length subsituteImageName:filename];
}

-(NSString*) getMediaAlbumArtAsBase64:(NSString*)guid withQuality:(NSNumber*)quality withLength:(NSNumber*)length subsituteImageName:(NSString* )filename
{
    NSString *base64 = nil;

    @autoreleasepool {
        UIImage* rawImage = [self getMediaAlbumArtAsUIImage:guid withQuality:quality withLength:length subsituteImageName:filename];
        NSData *imageData = nil;

        if (rawImage != nil)
        {
            @autoreleasepool {
                //this causes memory to not be released
                imageData = UIImageJPEGRepresentation(rawImage, [quality floatValue]);
                base64 = [imageData base64EncodedStringWithOptions:0];
            }
        }
    }

    return base64;
}

-(UIImage*)  getMediaAlbumArtFromMediaItemAsUIImage:(MPMediaItem*)item withQuality:(NSNumber*)quality withLength:(NSNumber*)length subsituteImageName:(NSString* )filename
{
    UIImage *rawImage = nil;

    @autoreleasepool {
        bool successfulArt = NO;

        if (item != nil)
        {
            MPMediaItemArtwork *albumArt = [item valueForProperty:MPMediaItemPropertyArtwork];

            if (albumArt != nil) {
                 @autoreleasepool {
                    //this causes memory to not be released
                    rawImage = [albumArt imageWithSize:CGSizeMake([length doubleValue], [length doubleValue])];
                    successfulArt = YES;
                }
            }
        }

        if (successfulArt == NO)
        {
            rawImage = [UIImage imageNamed:filename];
        }
    }

    return rawImage;
}

所以是的 - 我的问题是:在内存分配和泄漏方面,我做错了什么?我目前的测试只使用专辑封面 - 所以" UIImage imageNamed"不应该是问题(来自它的缓存)。另外,我读过ARC无法发布CoreGraphics对象,这也可能是问题所在。

我真的可以用这个帮助!谢谢!

1 个答案:

答案 0 :(得分:0)

我遇到了同样的问题。我认为框架中存在一个不释放内存的错误。基本上,每次调用func imageWithSize(size: CGSize) -> UIImage?时,分配的内存都会出现大幅增长。

如果它对你有帮助,我注意到如果你调用这个函数传入artwork.bounds.size(而不是每次都创建一个新的图像大小),那么内存只被分配一次并再次调用imageWithSize(使用相同的尺寸)不会重新分配新的内存。仅当您传入原始图稿图像的大小而不返回自定义大小时,才会出现这种情况。如果您需要自定义大小,也许您可​​以自己调整UIImage的大小,而不是依赖于这种错误的方法。