Warning: file_get_contents(/data/phpspider/zhask/data//catemap/4/matlab/16.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181

Warning: file_get_contents(/data/phpspider/zhask/data//catemap/2/image-processing/2.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
Matlab 在一个条件下,查找图像中像素的索引_Matlab_Image Processing_Matrix - Fatal编程技术网

Matlab 在一个条件下,查找图像中像素的索引

Matlab 在一个条件下,查找图像中像素的索引,matlab,image-processing,matrix,Matlab,Image Processing,Matrix,我有一个包含4个值{3,-3,1,-1}的图像,如图所示 让我们调用像素的索引,使其值等于轮廓中的1或-1像素。这些像素将创建一个围绕黄色(-3)的轮廓。现在,我想找到轮廓中的所有索引像素,并加上填充位置(向内和向外轮廓)。作为红色,填充设置为1,因此,这些像素的索引包括轮廓{1,-1}中的像素和作为红色的填充索引。在这个任务中,我想找到所有的像素索引。如何在matlab代码中实现这个想法。这是我在等高线中查找索引的代码 %% Let define the image I idx=find(I

我有一个包含4个值{3,-3,1,-1}的图像,如图所示

让我们调用像素的索引,使其值等于轮廓中的1或-1像素。这些像素将创建一个围绕黄色(-3)的轮廓。现在,我想找到轮廓中的所有索引像素,并加上填充位置(向内和向外轮廓)。作为红色,填充设置为1,因此,这些像素的索引包括轮廓{1,-1}中的像素和作为红色的填充索引。在这个任务中,我想找到所有的像素索引。如何在matlab代码中实现这个想法。这是我在等高线中查找索引的代码

%% Let define the image I
idx=find(I==1|I==-1);
padding=1;
%%Continue
更新:我的预期结果如上图中白色区域所示。因此,指数如13,14,15,…21,24

更新

首先,感谢Andrew和Rayryeng的回答。我想解决我的问题。如上所述,轮廓由{1,-1}创建。现在,我想忽略1和-1,所以图像只有{3,-3}。我定义的轮廓是{3,-3}边缘的像素,如图。保持填充和像素索引的相同想法。如何找到轮廓内和轮廓附近像素的索引(称为轮廓窄带)(预期结果为白色)

假设您的图像是N×M像素。在MATLAB中,数组按列顺序存储(有关更多信息,请参阅)。您可以按如下列格式使用
I
。首先,轮廓像素由

idx=find(I(:)==1|I(:)==-1);
现在,如果您希望向下和向上填充,则非常简单:

idx_up=idx - padding;
idx_up = idx_up(idx_up>0);
idx_down=idx + padding;
idx_down = idx_down(idx_down<=N*M);
并组合整体像素:

PaddedContour = false(N,M);
PaddedContour(unique([idx;idx_up;idx_down;idx_left;idx_right])) = true;

假设你的图像是N×M的皮克斯。在MATLAB中,数组按列顺序存储(有关更多信息,请参阅)。您可以按如下列格式使用
I
。首先,轮廓像素由

idx=find(I(:)==1|I(:)==-1);
现在,如果您希望向下和向上填充,则非常简单:

idx_up=idx - padding;
idx_up = idx_up(idx_up>0);
idx_down=idx + padding;
idx_down = idx_down(idx_down<=N*M);
并组合整体像素:

PaddedContour = false(N,M);
PaddedContour(unique([idx;idx_up;idx_down;idx_left;idx_right])) = true;

不太难,你走对了。如果您有图像处理工具箱,我建议您看看。特别是你想使用我的代码有你需要的所有细节

%rather than using find, we create a binary mask. Its not the indicies of
%the matching elements as find gives. its is 1/true if the value matches the
%criteria, and 0/false otherwise.
mask = (im=1 | im=-1);

%create a 3x3 rectangle structuring element. We use a 3x3 because we want
%to expand the image by one pixel. basically the structring element (Strel)
%is our kernal, if you know image processing this is the same thing. 
%a = [0 0 0 0;
%     0 1 1 1;
%     0 1 1 1;
%     0 1 1 1];
%our kernal is center at 2,2 (for this example) which are these elements
%     0 0 0  of a  think a(1:3,1:3) now what the dialate operation
%     0 1 1  says is, if the majority of these pixels are ones... they
%     0 1 1  should probabaly all be ones so all those 0s will become ones
%the size of the kernal 3x3 ensures we are only growing our image one
%pixel, hope that makes sense    
se = strel('square',3);

%now we dilate, or 'expand' our mask with our structuring element
expanded_mask = imdilate(mask,se);

%if you still want the indicies you can use find on our expanded mask
idx = find(expanded_mask==1);
编辑:无形态学操作/图像处理工具箱 这种方法使用了大量for循环,因此它不是最快的,并且不进行错误检查,但它可以工作。我的放大函数说,如果大多数像素都是1,那么它们都是1

function expanded_mask=DilateBinaryImage(bin_im, kernal_size)
    [max_row,max_col] = size(bin_im);

    %since we are opening the mask (only adding 1s), we can start off with the
    %same values of the mask, and simply add extra 1's as needed
    expanded_mask = bin_im;

    %we don't want to go off the edge of our image with this kernal
    %so we offset it a bit
    kern_padding = floor(kernal_size/2);

    %this ignores the edges
    for (curr_row=kern_padding+1:1:max_row - kern_padding)
       for (curr_col=kern_padding+1:1:max_col - kern_padding)
          %we do 2 sums, one for rows, one for columns
          num_ones = sum(sum(bin_im(curr_row-kern_padding:curr_row+kern_padding,curr_col-kern_padding:curr_col+kern_padding)));

          %if the majority of vlaues are 1, we use floor to help with corner
          %cases
          if (num_ones >= floor((kernal_size*kernal_size)/2))
              %make all the values one
              expanded_mask(curr_row-kern_padding:curr_row+kern_padding,curr_col-kern_padding:curr_col+kern_padding) = 1;
          end
       end
    end


end
然后就这样叫它

kernal_size= 3;
mask = (I==1 | I==-1);
expanded_mask = DilateBinaryImage(mask, kernal_size);
idx = find(expanded_mask==1);

我的扩张函数在二值图像的边缘不起作用。它只是精确地复制它们。

不太难,你走对了方向。如果您有图像处理工具箱,我建议您看看。特别是你想使用我的代码有你需要的所有细节

%rather than using find, we create a binary mask. Its not the indicies of
%the matching elements as find gives. its is 1/true if the value matches the
%criteria, and 0/false otherwise.
mask = (im=1 | im=-1);

%create a 3x3 rectangle structuring element. We use a 3x3 because we want
%to expand the image by one pixel. basically the structring element (Strel)
%is our kernal, if you know image processing this is the same thing. 
%a = [0 0 0 0;
%     0 1 1 1;
%     0 1 1 1;
%     0 1 1 1];
%our kernal is center at 2,2 (for this example) which are these elements
%     0 0 0  of a  think a(1:3,1:3) now what the dialate operation
%     0 1 1  says is, if the majority of these pixels are ones... they
%     0 1 1  should probabaly all be ones so all those 0s will become ones
%the size of the kernal 3x3 ensures we are only growing our image one
%pixel, hope that makes sense    
se = strel('square',3);

%now we dilate, or 'expand' our mask with our structuring element
expanded_mask = imdilate(mask,se);

%if you still want the indicies you can use find on our expanded mask
idx = find(expanded_mask==1);
编辑:无形态学操作/图像处理工具箱 这种方法使用了大量for循环,因此它不是最快的,并且不进行错误检查,但它可以工作。我的放大函数说,如果大多数像素都是1,那么它们都是1

function expanded_mask=DilateBinaryImage(bin_im, kernal_size)
    [max_row,max_col] = size(bin_im);

    %since we are opening the mask (only adding 1s), we can start off with the
    %same values of the mask, and simply add extra 1's as needed
    expanded_mask = bin_im;

    %we don't want to go off the edge of our image with this kernal
    %so we offset it a bit
    kern_padding = floor(kernal_size/2);

    %this ignores the edges
    for (curr_row=kern_padding+1:1:max_row - kern_padding)
       for (curr_col=kern_padding+1:1:max_col - kern_padding)
          %we do 2 sums, one for rows, one for columns
          num_ones = sum(sum(bin_im(curr_row-kern_padding:curr_row+kern_padding,curr_col-kern_padding:curr_col+kern_padding)));

          %if the majority of vlaues are 1, we use floor to help with corner
          %cases
          if (num_ones >= floor((kernal_size*kernal_size)/2))
              %make all the values one
              expanded_mask(curr_row-kern_padding:curr_row+kern_padding,curr_col-kern_padding:curr_col+kern_padding) = 1;
          end
       end
    end


end
然后就这样叫它

kernal_size= 3;
mask = (I==1 | I==-1);
expanded_mask = DilateBinaryImage(mask, kernal_size);
idx = find(expanded_mask==1);


我的扩张函数在二值图像的边缘不起作用。它只是精确地复制它们。

我很难理解您的问题描述。您能否突出显示上图中哪些像素位置将被发送到输出?你能给我们更多的例子吗?我可能已经看过你的问题描述至少5次了,但我仍然不明白你在找什么。@rayryeng:对不起,我的英语这么差。让我看看我的更新第11排应该是绿色的吗?还是白色?对不起。我错了。我会更新它。顺便说一句,我找到了一个使用精明的边缘检测的解决方案,但它需要很长时间。我很难理解你的问题描述。您能否突出显示上图中哪些像素位置将被发送到输出?你能给我们更多的例子吗?我可能已经看过你的问题描述至少5次了,但我仍然不明白你在找什么。@rayryeng:对不起,我的英语这么差。让我看看我的更新第11排应该是绿色的吗?还是白色?对不起。我错了。我会更新它。顺便说一句,我找到了一个解决方案,使用了精明的边缘检测,但它需要很长时间。非常有效。这是我以前读过的一种算法。读了你的实现之后,我想起了它。如果不用形态学运算,用其他方法找到它怎么样。你能用数学方法向我推荐吗?@user8430-形态膨胀相当于一个最大过滤器。查看局部像素邻域,输出是邻域内的最大值。如果您还记得我们前面谈到的
im2col
,您可以将像素邻域分解为列,取每列的最大值,然后使用
col2im
将输出重建回图像。这是一个好主意。这个想法基于一个窗口,它的中心是轮廓上的像素。对于轮廓中的每个像素,我们找到最大索引(3)和最小索引(-3)(我想)。这些指标将构成一个狭窄的区域。是吗?如果没有图像处理工具箱,ThPs方法非常有效。我添加了一个新的解决方案,该解决方案不使用工具箱,但仍然模拟了扩张功能。它不是健壮的,也可能不适用于所有情况,但它只是一个快速的解决方案谢谢。你能看看我的最新问题吗?非常完美。这是我以前读过的一种算法。读了你的实现之后,我想起了它。如果不用形态学运算,用其他方法找到它怎么样。你能用数学方法向我推荐吗?@user8430-形态膨胀相当于一个最大过滤器。查看局部像素邻域,输出是邻域内的最大值。如果您还记得我们前面谈到的
im2col
,您可以将像素邻域分解为列,取每列的最大值,然后使用
col2im
将输出重建回图像。这是一个很好的id