Матрица в матлабе? - PullRequest
       11

Матрица в матлабе?

1 голос
/ 23 ноября 2011

Я работаю над маркировкой подключенных компонентов, и моя матрица:

 1     1     0     2     2     2     0     3
 1     1     0     2     0     2     0     3
 1     1     1     1     0     0     0     3
 0     0     0     0     0     0     0     3
 4     4     4     4     0     5     0     3
 0     0     0     4     0     5     0     3
 6     6     0     4     0     0     0     3
 6     6     0     4     0     7     7     7

, и теперь я хочу выполнить второе сканирование, для этого я сделал следующий код:

for i=1:1:r
    for j=1:1:c
        if (bw(i,j)>=1) 

            if (i-1>0 & i+1<=r) 
                % if ( bw(i,j)~= bw(i-1,j) | bw(i,j)~= bw(i+1,j))
                if ( (bw(i,j)~= bw(i-1,j) & bw(i-1,j)>0))
                    bw(i,j)= min (bw(i-1,j),bw(i,j))
                elseif ((bw(i,j)~= bw(i+1,j) & bw(i+1,j)>0))
                    bw(i,j) = min(bw(i+1,j),bw(i,j));
                end
            end

            if (j-1>0 & j+1<=c) 
                if ( (bw(i,j)~= bw(i,j-1) & bw(i,j-1)>0))
                    bw(i,j) = min (bw(i,j-1),bw(i,j));
                elseif((bw(i,j)~= bw(i,j+1) & bw(i,j+1)>0))
                    bw(i,j) = min (bw(i,j+1),bw(i,j))  ; 
                end
            end

        end
    end
end
disp(bw);

но проблема в том, что когда я запускаю этот код, я получаю следующий вывод

 1     1     0     2     2     2     0     3
 1     1     0     1     0     2     0     3
 1     1     1     1     0     0     0     3
 0     0     0     0     0     0     0     3
 4     4     4     4     0     5     0     3
 0     0     0     4     0     5     0     3
 6     6     0     4     0     0     0     3
 6     6     0     4     0     7     7     7

только одно значение изменяется (2-я строка, 4 столбца) в моем результате, тогда как я хочу:

     1     1     0     1     1     1     0     3
     1     1     0     1     0     1     0     3
     1     1     1     1     0     0     0     3
     0     0     0     0     0     0     0     3
     4     4     4     4     0     5     0     3
     0     0     0     4     0     5     0     3
     6     6     0     4     0     0     0     3
     6     6     0     4     0     3     3     3

Может кто-нибудь помочь?где я ошибаюсь?

Ответы [ 2 ]

2 голосов
/ 23 ноября 2011

Отличное решение от Jonas. Поскольку я немного разбирался в кодировании, когда увидел, что он добавлен, я решил показать вам и мое решение. Надеюсь, это немного больше похоже на ваш оригинальный код.

Одна из ошибок, которую вы сделали, заключалась в том, что эта связь могла быть сделана всего за один проход. Как правило, это невозможно, так как обнаружение некоторых «элементов змеи» зависит от того, как вы выполняете итерацию по матрице. В связи с этим я добавил внешний цикл while.

 bw =[  1     1     0     2     2     2     0     3;
        1     1     0     2     0     2     0     3;
        1     1     1     1     0     0     0     3;
        0     0     0     0     0     0     0     3;
        4     4     4     4     0     5     0     3;
        0     0     0     4     0     5     0     3;
        6     6     0     4     0     0     0     3;
        6     6     0     4     0     7     7     7 ];


 %Set up matrix   
 [r,c] = size(bw);   

 %Zero pad border
 bwZ = [zeros(1,c+2);[zeros(r,1) bw zeros(r,1)];zeros(1,c+2)];

 %Iterate over all elements within zero padded border
 done=0;%Done flag 
 cc=1;  %Infinite loop protection
 while not(done) && cc<r*c
     done=1;cc=cc+1;
     for i=2:r+1
         for j=2:c+1
            %Point should be evaluated
            p = bwZ(i,j);
            if p >= 1
                %Pick out elements around active elements
                if bwZ(i-1,j)==0;ue=inf;else ue = bwZ(i-1,j); end;%Up element
                if bwZ(i+1,j)==0;de=inf;else de = bwZ(i+1,j); end;%Down element
                if bwZ(i,j-1)==0;le=inf;else le = bwZ(i,j-1); end;%Left element
                if bwZ(i,j+1)==0;re=inf;else re = bwZ(i,j+1); end;%Right element

                bwZ(i,j) = min([ue de le re]);
                %Set flag, if something has changed 
               if bwZ(i,j) ~= p
                    done = 0;
               end
            end
         end
     end
 end

 %Remove zero padding
 bw = bwZ(2:end-1,2:end-1)

Выход:

bw =

 1     1     0     1     1     1     0     3
 1     1     0     1     0     1     0     3
 1     1     1     1     0     0     0     3
 0     0     0     0     0     0     0     3
 4     4     4     4     0     5     0     3
 0     0     0     4     0     5     0     3
 6     6     0     4     0     0     0     3
 6     6     0     4     0     3     3     3
2 голосов
/ 23 ноября 2011

Если цифры не нужно сохранять, вы можете просто позвонить bwlabel на исходное изображение:

newImage = bwlabel(originalImage>0);

РЕДАКТИРОВАТЬ

Вот еще одинверсия.Он проверяет каждый подключенный компонент, чтобы убедиться, что к нему подключен другой подключенный компонент.Если да, то подключенный компонент перемаркируется.

%# nCC: number of connected components
nCC = max(originalImage(:));

for cc = 1:nCC
%# check whether the component exists
myCC = originalImage==cc;
if any(any(myCC))

   %# create a mask to check for neighbors
   %# by creating a border of 1 pixel
   %# around the original label
   msk = imdilate(myCC,true(3)) & ~myCC;

   %# read all the pixel values under the mask
   neighbours = originalImage(msk);

   %# we're not interested in zeros, remove them
   neighbours = neighbours(neighbours > 0);

   if ~isempty(neighbours)
   %# set the label of all neighbours to cc
   originalImage( ismember(originalImage,neighbours) ) = cc;
   end
end
end
...