在matlab中选择与像素重叠的对象

时间:2014-02-13 06:26:06

标签: matlab data-structures

我正在Matlab中实现某种泛洪填充算法,给定二进制图像中的起始像素,将输出仅包含可直接连接到它的像素的二进制图像。

基本上,让

foo =
     1     1     1
     1     0     0
     1     0     1

调用flood_fill(foo,1,1)会产生

     1     1     1
     1     0     0
     1     0     0

现在,我对Matlab很新。我最初以递归样式实现flood_fill,但Matlab的值传递行为使得处理大图像的效率非常低。为了解决这个问题,我重新实现了flood_fill这样的

function [outImage] = flood_fill(inImage,start_x,start_y)
    width = size(inImage,2);
    height = size(inImage,1);

    outImage = zeros(height,width);

    points = [];
    points = [points; [start_x start_y]];

    while size(points,1)>0
        point = points(1,:);
        points = points(2:end,:);
        y=point(2);
        x=point(1);

        outImage(y,x)=1;

        if (y>1 && (outImage(y-1,x)==0) && (inImage(y-1,x)==1))
            points = [points; [x y-1]];
        end
        if (y<height && (outImage(y+1,x)==0) && (inImage(y+1,x)==1))
            points = [points; [x y+1]];
        end
        if (x>1 && (outImage(y,x-1)==0) && (inImage(y,x-1)==1))
            points = [points; [x-1 y]];
        end
        if (x<width && (outImage(y,x+1)==0) && (inImage(y,x+1)==1))
            points = [points; [x+1 y]];
        end
    end
end 

现在,这适用于小型矩阵/图像,但也可以永久保存在大型图像上。我怀疑为什么大量的数组调整大小正在进行中。通常(在C ++中),我使用无序链表并将其用作堆栈(从头部移除并插入)以避免代价高昂的数组调整大小。

Matlab中是否存在这样的数据结构?如果没有,我可以用什么Matlab成语?也许是内置功能?

2 个答案:

答案 0 :(得分:2)

您搜索的名为bwselect的函数:

foo=[1 1 1; 1 0 0; 1 0 1]
b=bwselect(foo,1, 1)

请注意,您还可以定义第四个输入n(例如:bwselect(foo,1,1,n)),其值可以为4以指定4个连接区域,或者8可以指定8个连接区域。

答案 1 :(得分:1)

Adiel回答了你的第二个问题“也许是一个内置函数?”。至于第一部分:

我不熟悉MATLAB中的链表。但是,您可以通过初始化点矩阵的大小来显着加快功能,并且在此之后不要更改大小。预初始化应该始终在MATLAB中完成。如果该函数不适用于固定大小的矩阵,我总是建议您尝试重写该函数。

针对您的具体情况:

function [outImage] = flood_fill(inImage,start_x,start_y)
    width = size(inImage,2);
    height = size(inImage,1);

    outImage = zeros(height,width);

    points = zeros(nnz(inImage),2);  % I take it this is the maximum size
    points(1,:) = [start_x start_y];

    k = 1;                           % Increment row number in points
    while size(points,1)>0

        k = k + 1;
        y=points(k, 2);
        x=points(k, 1);

我理解你一般都有编程技巧,所以我相信你应该能够将剩下的代码改编成新的格式。 (我没时间通过它并重写它)。我很确定它会更快地运行 更多