2012-01-16 3 views
2

간략 알고리즘을 이해하기 위해 Matlab에서 내 자신의 간접 알고리즘을 구현하려고합니다. http://fourier.eng.hmc.edu/e161/lectures/morphology/node2.html을 따르고 있으며 내 자신의 코드를 구현하고 있지만 그 결과가 정확하지 않습니다. 여기 MATLAB에서 간접 알고리즘 이해 및 구현

내 코드이다 : 위 사이트에서

%for the sake of simplicity, the outermost pixels are ignored. 
for x = 2:1:511 
    for y = 2:1:511 

     % if this pixel is not black, then, proceed in. 
     if (frame2(y,x) > 0)     

      % the pos(1 to 8) here are for the surrounding pixels. 
      pos(1) = frame2(y-1,x-1); 
      pos(2) = frame2(y, x-1); 
      pos(3) = frame2(y+1, x+1); 
      pos(4) = frame2(y+1, x); 
      pos(5) = frame2(y+1, x-1); 
      pos(6) = frame2(y, x-1); 
      pos(7) = frame2(y-1, x-1); 
      pos(8) = frame2(y-1, x); 

      nonZeroNeighbor = 0; 
      transitSequence = 0; 
      change = 0; 

      for n = 1:1:8 
       % for N(P1) 
       if (pos(n) >= 1) 
        nonZeroNeighbor = nonZeroNeighbor + 1; 
       end 

       % for S(P1) 
       if (n > 1) 
        if (pos(n) ~= change) 
         change = pos(n); 
         transitSequence = transitSequence + 1; 
        end 
       else 
        change = pos(n); 
       end 

      end 

      % also for S(P1) 
      if ((nonZeroNeighbor > 1 && nonZeroNeighbor < 7) || transitSequence >= 2) 
       markMatrix(y,x) = 1; 
       fprintf(1, '(%d,%d) nonzero: %d transit: %d\n', y,x, nonZeroNeighbor, transitSequence); 
      else %this else here is for the reverse. 

      end 

     end 
    end 
end 


    for x = 2:1:511 
     for y = 2:1:511 
      if (markMatrix(y,x) > 0) 
       frame2(y,x) = 0; 
      end 
     end 
    end 

    savePath = [path header number2 '.bmp']; 

    imwrite(frame2, savePath, 'bmp'); %output image here, replacing the original 

, 그와 같은 함수 S (P1)을 말한다 :

"S (P1) : 0 또는 1의 수 (또는 (P2, P3, ..., P9)에서의 천이 "

이 부분의 코드는"% (S) "와"% (S))" 코멘트. 이 함수를 올바르게 구현하고 있습니까? 내가 가지고있는 출력 이미지는 단순히 비어 있습니다. 전혀.

정확한 출력을 위해 논리적 인 문제가 있음을 알고 있습니다. 사이트에 관해서는

모양의 일부가 2 픽셀 너비 인 경우 모든 픽셀이 경계 지점이며 표시되고 삭제됩니다.

이 문제는 현재 무시해야합니다.

+1

패스 1 룰 주 : * 표 모든 에지 화소 P1 = 1 ** 적어도 하나 개의 조건을 만족하지 *. 이 경우에는'transitSequence'가 2보다 작아야한다고 생각합니다. 왜냐하면 중심 픽셀을 표시하기 위해서입니다. 또한 '0-1-0' 또는'1-0-1 '시퀀스는 단일 중계 시퀀스로 해석되며 두 번 ('0-> 1 '과'1-> 0 '모두) 계산됩니다. . 가장 간단한 방법은 루프 (change = pos (8)) 앞에 P (8)에'change '를 설정 한 다음 루프 다음에'transitSequence'를 2로 나누는 것입니다. – Groo

+0

나는 당신이 change = pos (8) 부분에 대해 옳다고 생각하며 if 문에서 "not"연산자를 잊어 버린 것처럼 보입니다. 그래서 if :(~ nonZeroNeighbor <= 1 || nonZeroNeighbor> = 7) || transitSequence <2) 이제 괜찮습니다. 고맙습니다. – Karl

+0

흠 ... 이상하게, 아무런 변화가 없을 때까지 알고리듬 루프를 만든 후에, 어쨌든, 나는 숱이없는 엣지를 보지 못한다. 나는 포인트 만 본다. 나는 아직도 내가 뭔가를 놓치고 있다는 느낌이 들었다 ... – Karl

답변

3

나는 문제를 해결하고 알고리즘을 작동시킬 수 있다고 생각했습니다. 도중에 몇 가지 작은 편집을했는데 (자세한 내용은 아래 코드를 참조하십시오), 초기 구현시 두 가지 근본적인 문제도 발견했습니다.

첫째, 1 단계와 2 단계의 첫 번째 단계에서 모두 수행되었다고 가정했지만 실제로 알고리즘을 이미지에서 잠시 동안 작동 시키도록해야합니다. 이것은 반복적 인 형태 학적 단계가 이미지에서 '먹는'경우에 전형적입니다. 이것은 while 루프가 추가 된 이유입니다.

둘째, S() 계산 방법이 잘못되었습니다. 0과 1, 1에서 0까지 두 단계를 세 었으며 두 번 계산하지 말아야하고 P (2)와 P (9) 주위에서 대칭을 처리하지 않았습니다.

내 코드 :

%Preliminary setups 
close all; clear all; 
set(0,'DefaultFigureWindowStyle','Docked') 

%Read image 
frame2 = imread('q1.jpg'); 

%Code for spesific images 
%frame2(:,200:end) = []; 
%frame2 = rgb2gray(frame2); 

%Make binary 
frame2(frame2 < 128) = 1; 
frame2(frame2 >= 128) = 0; 

%Get sizes and set up mark 
[Yn Xn] = size(frame2); 
markMatrix = zeros(Yn,Xn); 

%First visualization 
figure();imagesc(frame2);colormap(gray) 
%% 

%While loop control 
cc = 0; 
changed = 1; 
while changed && cc < 50; 

    changed = 0; 
    cc = cc + 1; 
    markMatrix = zeros(Yn,Xn); 

    for x = 2:1:Xn-1 
     for y = 2:1:Yn-1 

      % if this pixel is not black, then, proceed in. 
      if (frame2(y,x) > 0)     

       % the pos(2 to 9) here are for the surrounding pixels. 
       pos(1) = frame2(y, x); 
       pos(2) = frame2(y-1, x); 
       pos(3) = frame2(y-1, x+1); 
       pos(4) = frame2(y, x+1); 
       pos(5) = frame2(y+1, x+1); 
       pos(6) = frame2(y+1, x); 
       pos(7) = frame2(y+1, x-1); 
       pos(8) = frame2(y, x-1); 
       pos(9) = frame2(y-1, x-1); 

       nonZeroNeighbor = 0; 
       transitSequence = 0; 
       change = pos(9); 

       for n = 2:1:9 

        %N() 
        nonZeroNeighbor = sum(pos(2:end)); 

        %S() 
        if (double(pos(n)) - double(change)) < 0 
         transitSequence = transitSequence + 1; 
        end 
        change = pos(n); 

       end 

       %Test if pixel is to be removed 
       if ~(nonZeroNeighbor == 0 || nonZeroNeighbor == 1 ... 
        ||nonZeroNeighbor == 7 || nonZeroNeighbor == 8 ... 
        ||transitSequence >= 2) 

         markMatrix(y,x) = 1; 
         fprintf(1, '(%d,%d) nonzero: %d transit: %d\n', ... 
          y,x, nonZeroNeighbor, transitSequence); 
       end 

      end 
     end 
    end 

    %Mask out all pixels found to be deleted 
    frame2(markMatrix > 0) = 0; 

    %Check if anything has changed 
    if sum(markMatrix(:)) > 0;changed = 1;end 

end 

%Final visualization 
figure();imagesc(frame2);colormap(gray) 

Lines before algorithm is run

Lines after algorithm is run

+0

최종 이미지의 라인은 실제로 보이는 것처럼 연결이 끊어져 있지 않습니다. 대부분 MATLAB에서 '1'을 모두 표시하지 않습니다. – Vidar

+0

bwmorph ('thin') 알고리즘처럼 작동하지 않습니다 ... –