FFT para detecção de linha

8

Estou tentando usar a FFT de uma maneira diferente da maioria das pessoas pergunta. Quero poder tirar uma foto de um gráfico com linhas verticais repetidas regularmente e processar a imagem para determinar em que distância em pixels as linhas estão em média. Tentei a detecção de arestas precisas e a detecção de linhas compactas e acho que não posso otimizar as imagens o suficiente para detectar com precisão apenas as linhas nas quais estou interessado.

Portanto, minha tentativa é digitalizar 10 linhas da imagem e acumular os valores de pixel em compartimentos correspondentes à coluna de pixels. O que resulta quando você faz um gráfico é uma forma de onda muito bonita. Quando executo uma DFT ou FFT sobre isso, encontro um pico que acredito ser a frequência da repetição da linha. (Isso pode ser uma suposição defeituosa)

Minha pergunta é: a que esse número corresponde? ou seja, acho que estou confuso com qual seria minha taxa de amostragem porque está em pixels. Eu acho que esse é um uso válido da FFT, mas estou caindo aqui no momento em que acho que devo ter sucesso.

Como um exemplo. Criei uma imagem com 300 pixels de largura. Existem linhas de largura de 1 pixel desenhadas em intervalos exatamente de 30 pixels. Encontrei 2 picos, um em 75 e outro em 225 (que parecem simétricos) para o componente real. (Não acredito que o componente imaginário deva ser reproduzido ??). Sei que as linhas estão separadas por 30 pixels. Como os 75 e ou 225 se relacionam?

Estou tentando realmente conseguir isso, e sou grato por qualquer ajuda que você possa recomendar. Neste ponto, estou desistindo da detecção de borda e quero tentar essa abordagem.

Agradeço antecipadamente.


fonte
Muito obrigado a todos por suas respostas! A FFT simplesmente não parece estar funcionando. Como eu adicionaria o componente imaginário? O programa que eu uso (stat plus) apenas cospe uma coluna de números reais e imaginários. Eu estava traçando o real no eixo x, mas tenho certeza de que há uma maneira melhor de incluir números imaginários. Além disso, eu segui o caminho da autocorrelação e obtive um resultado! doce !, mas sempre traz mais perguntas. O resultado obtido é o dobro do tamanho da imagem original (compreensivelmente), que oscilações muito mais limpas perto do centro. Existe alguma rima ou razão para

Respostas:

6

Você pode tentar a Autocorrelação para isso. Aqui está uma resposta SO descrevendo como executar a autocorrelação com o Matlab usando FFTs. Isso pode ser estendido para duas dimensões.

Eu implementei seu caso de teste em numpy da seguinte maneira:

a = np.zeros(300)
a[::30] = 1
plt.acorr(a, maxlags=50)

Isso fornece o seguinte gráfico:

insira a descrição da imagem aqui

Como você pode ver, os picos aparecem em +/- 30.

mevatron
fonte
4

Se houver 10 linhas verticais em sua imagem, um FFT de uma linha de varredura horizontal completa (300 pix) deve mostrar algum conteúdo de magnitude em torno da bandeja 10 ou da bandeja 11. A bandeja 75 de 300 indica que algo está acontecendo a cada 4 pixels, ou tão.

Você realmente precisa observar a magnitude do resultado da FFT, não apenas o componente "real" (realmente o componente par) porque, se suas linhas de grade estiverem fora do centro, o conteúdo espectral poderá aparecer como estranho (portanto, "imaginário" no resultado da FFT).

Dada a entrada real de uma FFT, os compartimentos de resultados acima de N / 2 (acima de 150 no seu caso) contêm apenas repetições dos mesmos dados, exceto conjugado complexo. Então você pode ignorá-los.

hotpaw2
fonte
0

FFTFFTFFT(1)(x+y))FFT

Não tenho muita certeza disso, mas algo me diz que a distância (em pixels) entre o pico e o centro indica a periodicidade. Depois de ter a periodicidade, você pode facilmente chegar à distância entre cada objeto.

rounak
fonte