Próbuję użyć transformacji Hougha do wykrywania krawędzi i chciałbym wykorzystać obrazy gradientowe jako podstawę.
Co zrobiłem do tej pory, ze względu na obraz I
wielkości [M,N]
i jej pochodnych cząstkowych gx
, gy
jest obliczenie kąta gradientu w każdym pikselu jako thetas = atan(gy(x,y) ./ gx
. Podobnie obliczam wielkość gradientu jako magnitudes = sqrt(gx.^2+gy.^2)
.
Aby zbudować transformację Hougha, używam następującego kodu MATLAB:
max_rho = ceil(sqrt(M^2 + N^2));
hough = zeros(2*max_rho, 101);
for x=1:M
for y=1:N
theta = thetas(x,y);
rho = x*cos(theta) + y*sin(theta);
rho_idx = round(rho)+max_rho;
theta_idx = floor((theta + pi/2) / pi * 100) + 1;
hough(rho_idx, theta_idx) = hough(rho_idx, theta_idx) + magnitudes(x,y);
end
end
Wynikowa transformacja Hougha wygląda wiarygodnie (patrz http://i.stack.imgur.com/hC9mP.png ), ale kiedy próbuję użyć jej maksimów jako parametrów krawędzi na oryginalnym obrazie, wyniki wyglądają mniej więcej losowo. Czy zrobiłem coś złego w konstruowaniu transformacji Hougha?
AKTUALIZACJA : Miałem głupi błąd w moim kodzie: rho
został obliczony jako x*cos(theta)+y*cos(theta)
zamiast x*cos(theta)+y*sin(theta)
. To znaczy, użyłem dwóch cosinusów zamiast cosinusa i sinusa. Edytowałem powyższy kod, a nowy wynikowy obraz znajduje się poniżej. Nie dało to jednak znacznie lepszych krawędzi.
@endolith: Aby wykreślić krawędź, biorąc pod uwagę maksymalną wartość w hough
macierzy na rho_idx, theta_idx
, tłumaczę indeksy na rho,theta
wartości:
theta = (theta_idx -1) / 100 * pi - pi / 2;
rho = rho_idx - max_rho;
Wreszcie wykreślam krawędź jako y= (rho - x*cos(theta)) / sin(theta)
.
źródło
Odpowiedzi:
Jestem trochę zdezorientowany twoim pytaniem. Przekształcenie Hougha służy do wykrywania linii, a nie krawędzi.
Jeśli wszystko, czego potrzebujesz, to mapa krawędzi, powinieneś po prostu przekroczyć wielkość gradientu lub użyć czegoś bardziej wymyślnego, takiego jak wykrywacz krawędzi Canny.
Jeśli chcesz wykryć linie proste, lepiej byłoby zacząć od mapy krawędzi, a następnie użyć
hough
funkcji, jeśli przybornik Przetwarzania obrazu, jeśli masz do niego dostęp. Problem z transformacją Hougha na gradiencie polega na tym, że piksele krawędziowe tworzące linię prostą mogą mieć przeciwne orientacje gradientu. Weźmy na przykład wzór szachownicy. Krawędź między dwoma rzędami kwadratów odwraca orientację w zależności od tego, czy masz czarny kwadrat powyżej i biały kwadrat poniżej, czy na odwrót.Jeśli chodzi o twoje wdrożenie, myślę, że problem polega na tym, że pojemniki w macierzy Hougha są za małe. Zasadniczo rozmiar pojemnika w wymiarze rho wynosi 1, a rozmiar pojemnika w wymiarze theta jest mniejszy niż 2 stopnie. Oznacza to, że orientacje gradientu muszą bardzo dokładnie wysunąć się, aby utworzyć linię, co rzadko zdarza się w praktyce. Jeśli ustawisz rho_idx i theta_idx, aby pojemniki były większe, sprawi to, że twój detektor linii będzie bardziej odporny na błędy i możesz uzyskać lepsze linie.
źródło
Nie mam pojęcia, czy jest to problem, ale atan () daje tylko kąty od -90 do +90 stopni z powodu dwuznaczności kwadrantu. Aby uzyskać pełny kąt gradientu (od -180 do 180), musisz użyć atan2 ().
źródło
atan2
, ale nie rozwiązało to problemów.