Objective c 泛洪填充内存泄漏

Objective c 泛洪填充内存泄漏,objective-c,c,core-graphics,flood-fill,Objective C,C,Core Graphics,Flood Fill,我正在用C为iPhone实现一个floodfill函数 填充工作,虽然我有两个问题 执行以下代码几次后,手机会发出内存警告。很可能是内存泄漏。还请注意,无符号字符*数据(图像数据)在泛光填充结束时处于空闲状态() (小问题)如果我试图将RGB颜色写入大于大约(r:200,g:200,b:200,a:200)的像素中,我会出现奇怪的伪影。解决方法是简单地限制值 我怀疑这两个问题之间可能有关联 下面的代码使用堆栈描述了我的洪水填充算法: .h: typedef struct { int re

我正在用C为iPhone实现一个
floodfill
函数

填充工作,虽然我有两个问题

  • 执行以下代码几次后,手机会发出内存警告。很可能是内存泄漏。还请注意,无符号字符*数据(图像数据)在泛光填充结束时处于空闲状态()

  • (小问题)如果我试图将RGB颜色写入大于大约(r:200,g:200,b:200,a:200)的像素中,我会出现奇怪的伪影。解决方法是简单地限制值

  • 我怀疑这两个问题之间可能有关联

    下面的代码使用堆栈描述了我的洪水填充算法:

    .h:

    typedef struct {
        int red;
        int green;
        int blue;
        int alpha;
    } GUIColor;
    
    
    struct pixel_st {
        int x;
        int y;
        struct pixel_st *nextPixel;
    };
    typedef struct pixel_st pixel;
    
    .m:

       void floodFill(CGPoint location, GUIColor tc, GUIColor rc, size_t width, size_t height, unsigned char *data){
        if (isGUIColorEqual(tc, rc)) return;
    
        pixel* aPixel = (pixel *) malloc(sizeof (struct pixel_st));
        NSLog(@"sizeof aPixel : %i",(int)sizeof(aPixel));
    
        (*aPixel).x = location.x;
        (*aPixel).y = location.y;
        (*aPixel).nextPixel = NULL;
    
        int i = 0;
    
        NSLog(@"Replacement color A%i, R%i, G%i, B%i",rc.alpha,rc.red,rc.green, rc.blue);
    
        while (aPixel != NULL){
            pixel *oldPixel_p = aPixel;
            pixel currentPixel = *aPixel;
            aPixel = currentPixel.nextPixel;
    
    
            //Now we do some boundary checks
            if (!isOutOfBounds(currentPixel.x, currentPixel.y, width, height)){
                //Grab the current Pixel color
                GUIColor currentColor = getGUIColorFromPixelAtLocation(CGPointMake(currentPixel.x, currentPixel.y), width, height, data);
    
                if (isGUIColorSimilar(currentColor, tc)){
                    //Colors are similar, lets continue the spread
                    setGUIColorToPixelAtLocation(CGPointMake(currentPixel.x, currentPixel.y), rc, width,height, data);
    
                    pixel *newPixel;
    
    
                    if ((newPixel = (pixel*) malloc(sizeof(struct pixel_st))) != NULL) {
                        (*newPixel).x = currentPixel.x;
                        (*newPixel).y = currentPixel.y-1;
                        (*newPixel).nextPixel = aPixel;
                        aPixel = newPixel;
    
                    }
                    if ((newPixel = (pixel*) malloc(sizeof(struct pixel_st))) != NULL) {
                        (*newPixel).x = currentPixel.x;
                        (*newPixel).y = currentPixel.y+1;
                        (*newPixel).nextPixel = aPixel;
                        aPixel = newPixel;
                    }
                    if ((newPixel = (pixel*) malloc(sizeof(struct pixel_st))) != NULL) {
                        (*newPixel).x = currentPixel.x+1;
                        (*newPixel).y = currentPixel.y;
                        (*newPixel).nextPixel = aPixel;
                        aPixel = newPixel;
                    }
                    if ((newPixel = (pixel*) malloc(sizeof(struct pixel_st))) != NULL) {
                        (*newPixel).x = currentPixel.x-1;
                        (*newPixel).y = currentPixel.y;
                        (*newPixel).nextPixel = aPixel;
                        aPixel = newPixel;
                    }
                    free(oldPixel_p);
                    i ++;
                    if (i == width * height * 4 * 5) break;
    
                }
    
    
            }
        }
    
        free(aPixel);
    }
    
    堆栈的此实现基于以下内容中的
    ObjFloodFill


    首先,循环中的每个
    如果((newPixel=(pixel*)malloc(…
    )分配了新的内存块,那么循环中有4个分配,只有1个解除分配


    其次,我不明白为什么不简单地使用堆栈上的对象?您真的需要在堆上分配newPixel、oldPixel等等吗?回顾一下实现,可能还有更简单的方法来实现同样的操作,而根本不需要管理内存问题。

    您需要移动
    oldPixel的解除分配_p
    if
    块之外,因为它总是“消耗”的


    另外,最后一个
    free
    仅释放列表中的第一个元素。列表可能有多个元素。您需要逐步遍历列表并释放所有剩余元素。

    为什么在堆栈基于ObjFloodFill的情况下,分配内存一次,然后在内部释放多次,我正在将其移植到我的代码中,但是我我对straight-C内存管理没有太多经验,所以我不确定。在页面顶部,它被标注为“OgreSwamp2年前在扫描线Floodfill中添加了注释,表示它不工作”ScanlineFloodfill算法不起作用,但4路算法起作用,我不确定其中的内存管理是否良好,虽然可能有,但我不确定如何进行,我以前使用过递归函数floodfill,但由于堆栈溢出,这会使设备崩溃(在iOS模拟器上它可以工作)。