Melhor maneira de segmentar veias em folhas?

47

Pesquisei bastante e descobri métodos como limiar adaptativo, divisor de águas, etc., que podem ser usados ​​para detectar veias nas folhas. No entanto, o limiar não é bom, pois introduz muito ruído

Todas as minhas imagens são cinzentas, por favor, alguém poderia sugerir quais abordagens adotar, considerando esse problema com necessidade urgente de ajuda

EDIT: Minha imagem original

insira a descrição da imagem aqui

Após limiar

insira a descrição da imagem aqui

Conforme sugerido pela resposta, tentei a seguinte detecção de borda

  1. Canny

Muito barulho e distúrbios indesejados

insira a descrição da imagem aqui

  1. Sobel

insira a descrição da imagem aqui

  1. Roberts

insira a descrição da imagem aqui

EDIT: Tentei mais uma operação, recebo o seguinte resultado é melhor do que o que eu tentei com astuto e adaptável O que você sente?

insira a descrição da imagem aqui

vini
fonte
Poderia nos mostrar algumas imagens?
Jonas
Eu adicionei imagens
vini
@vini Você está fazendo isso atualmente como uma etapa de pré-processamento para obter uma boa correspondência de modelos mais tarde? Além disso, como você conseguiu a segunda imagem, através de limiares simples?
Spacey
Meu objetivo é obter o melhor resultado possível em segmentar as veias para que o meu doesnt saída contêm artefatos dispersos, eu usei limiar adaptativo para obter a segunda imagem
vini
A partir das imagens que você forneceu, parece que você está usando (vários) filtros em uma imagem com limite. Isso dará resultados extremamente ruins. Você deve usar os filtros na imagem original e limitar sua saída.
Benjohn 26/01

Respostas:

56

Você não está procurando arestas (= bordas entre áreas estendidas de alto e baixo valor de cinza), está procurando arestas (linhas finas mais escuras ou mais brilhantes que a vizinhança); portanto, os filtros de arestas podem não ser o ideal: um filtro de aresta será dê a você dois flancos (um de cada lado da linha) e uma resposta baixa no meio da linha:

amostras de filtro

ADICIONAR : Se você foi solicitado a explicar a diferença entre um detector de borda e um detector de cume mais claramente. Peço desculpas antecipadamente se esta resposta estiver ficando muito longa.

Um detector de borda é (geralmente) o primeiro operador derivado: se você imaginar a imagem de entrada como uma paisagem 3D, um detector de borda mede a inclinação da inclinação em cada ponto da paisagem:

insira a descrição da imagem aqui

Se você deseja detectar a borda de uma região brilhante ou escura estendida, tudo bem. Mas, para as veias da imagem do OP, você fornecerá exatamente o mesmo: os contornos esquerdo e direito de cada veia:

insira a descrição da imagem aqui

Isso também explica o "padrão de linha dupla" nos resultados do detector de borda Canny:

insira a descrição da imagem aqui

gxy

g(x,y)12x22gx2+xy2gxy+12y22gy2+xgx+ygy+g(0,0)

ou, em forma de matriz:

g(x,y)12(xy).(2gx22gxy2gxy2gy2).(xy)+(xy).(gxgy)+g(0,0)

(2gx22gxy2gxy2gy2)

λ1x2+λ2y2λ1λ2

Que tipo de formas essa aproximação de função pode ter? Na verdade, não tantos:

insira a descrição da imagem aqui

Para detectar sulcos, queremos encontrar áreas na imagem que se pareçam com a última das plotagens acima, portanto, estamos procurando áreas em que o autovalor principal do Hessian seja grande (comparado ao autovalor menor). A maneira mais simples de detectar isso é apenas calcular o valor próprio principal em cada pixel - e é isso que o filtro de crista abaixo faz.


Um filtro de cume provavelmente dará melhores resultados. Eu tentei o Mathematica embutido RidgeFilter(que calcula o principal autovalor da matriz Hessian em cada pixel) na sua imagem:

filtro de cume

Como você pode ver, há apenas um pico para cada linha fina e escura. Rendimentos de binarização e esqueletização:

insira a descrição da imagem aqui

Depois de podar o esqueleto e remover pequenos componentes (ruído) da imagem, recebo este esqueleto final:

insira a descrição da imagem aqui

Código completo do Mathematica:

ridges = RidgeFilter[ColorNegate@src];
skeleton = SkeletonTransform[Binarize[ridges, 0.007]];
DeleteSmallComponents[Pruning[skeleton, 50], 50]

ADICIONAR, ACRESCENTAR:

Não sou especialista em Matlab, não sei se ele possui um filtro de cume interno, mas posso mostrar como implementá-lo "manualmente" (novamente, usando o Matematica). Como eu disse, o filtro de crista é o principal autovalor da matriz de Hessian. Eu posso calcular esse valor próprio simbolicamente no Mathematica:

eigenvalue=Last[Eigenvalues[(HxxHxyHxyHyy)]]

12(Hxx+Hyy+Hxx2+4Hxy2-2HxxHyy+Hyy2)

HxxHxyHyy

Niki Estner
fonte
Sim isso é exatamente o que eu quero no entanto eu estou fazendo isso em Matlab e encontrar um equivalente do filtro cume tornou-se difícil
vini
1
@nikie Resposta muito boa - pergunta - você pode explicar a diferença entre um detector de borda e um detector de cume para nós, pessoas que não processam imagens? Obrigado novamente
Spacey
@Mohammad: Eu tentei, eu espero que eu fiz isso um pouco mais claro agora, apesar da matemática
Niki Estner
i tentou filtro cume não dá resultados satisfatórios
vini
2
@ vini: "não dá resultados satisfatórios" realmente não me diz muito. Você tem a mesma imagem de resultado que eu publiquei? O que é "não satisfatório"?
Niki Estner 19/03/12
6

Ao usar a detecção de borda Canny (em Halcon), com alfa sendo 1 e o limite baixo 8 e o limite alto 13 (em uma escala de 1-255), obtenho o seguinte resultado:

Folha de detecção de borda flexível

Com os ajustes dos parâmetros, o resultado obtido com o Canny pode ser muito mais aprimorado. Usando esta imagem, você pode pular as bordas curtas para remover o ruído e conectar as bordas longas para o resultado final.

Entre: uma cor diferente indica uma borda diferente.

Posso obter um resultado bastante semelhante usando este detector de borda Canny online :

  • Escolha a imagem I9Pxl.png
  • Sigma 1.2
  • T-baixo 0,04
  • T-alto 0,07
  • Outras configurações padrão
  • Clique na visualização de atualização para obter o resultado
Geerten
fonte
Obrigado :) Eu acho que Canny é apenas o melhor;) Btw, aplicando Canny em seu resultado pode produzir resultados ainda melhores ..
Geerten
BTW: Se você não percebeu: Quais são as limitações de um detector de borda Canny? Você pode dar sua opinião aqui!
Dipan Mehta 15/03/12
Se você está me dizendo: eu já dei a minha opinião na sua pergunta. Se você estiver dando um comentário em geral: eu excluirei este comentário.
Geerten
Ah, sim, eu não percebi isso!
Dipan Mehta 15/03/12
Obrigado pela sua resposta doesnt no entanto prudente preservar detalhes de veias nas folhas que não são detectados como você mostrou ...
vini
6

Seguindo a excelente resposta acima, veja como fazê-lo em python usando as funções do scikit.

from skimage.feature import hessian_matrix, hessian_matrix_eigvals

#assume you have an image img

hxx, hxy, hyy = hessian_matrix(img, sigma=3)
i1, i2 = hessian_matrix_eigvals(hxx, hxy, hyy)

#i2 is the variable you want.

#Visualise the result
import matplotlib.pyplot as plt
plt.imshow(i2)
Matthew Shun-Shin
fonte
O que imgdeveria ser? Eu tenho um pngarquivo e ele não funciona.
Sigur
img deve ser uma matriz numpy 2D.
Matthew Shun-Shin
Na verdade, i1é o maior dos autovalores, portanto, você deve usá-lo.
27417 Rob
Esta é a explicação mais clara que eu já vi!
Eureka
3

Em vez de limiar, apliquei a detecção de borda simples.

GIMP usado com diferença de Gaussian - Radious Outer: 3.0 e Inner: 1.0.

Aqui está como é.

insira a descrição da imagem aqui

Você também pode aplicar um filtro mediano ou erosão / dilatação para remover parte do ruído granulado.

Aqui está a página que explica a implementação do gimp.

Você deve consultar técnicas diferentes, como Laplaciano de Gaussiano ou Diferença de Gaussin, etc. Veja o seguinte: http://homepages.inf.ed.ac.uk/rbf/HIPR2/log.htm#7

E esta resposta Como o Laplacian é usado para a Máscara Unsharp?

Dipan Mehta
fonte
GIMP? é qual detector de borda?
vini 14/03
1
Não - é um pacote de edição de imagens. Foi uma verificação rápida - apenas para indicar um ponto. - use a detecção de borda em oposição à limiarização.
Dipan Mehta 14/03/12
Qual detector de borda o GIMP usa? Lamento ter muito pouco conhecimento dela
vini
@vini adicionou referência.
Dipan Mehta 14/03/12
3

Este tópico sempre atraiu muito interesse e, no entanto, não existe um consenso real sobre o assunto. Por isso, decidi soltar algumas palavras.

Minhas respostas para perguntas semelhantes feitas anteriormente sobre stackexchange ( Q1 e Q2 ) envolveram um algoritmo de extração de estrutura curvilínea subpixel por Steger. Este método teve um desempenho razoavelmente bom em muitos casos e, felizmente, incluindo este. Portanto, eu posto a imagem de saída aqui: insira a descrição da imagem aqui e aqui com uma configuração de parâmetro diferente e sem coloração de conexão: insira a descrição da imagem aqui Para obter detalhes e referências apropriadas, consulte os posts de troca de pilha a que me referi.

Tolga Birdal
fonte
0

Como parte do meu último ano de estudos de engenharia, tive que estudar métodos de segmentação de vasos sanguíneos em imagens de fundo ocular. Achei esse método de reconstrução de árvores (de Cohen, Laurent D. e Mille, Julien particularmente interessante de usar junto com os métodos de marcha rápida).

Outros documentos que você pode querer procurar:

  • Contornos ativos geodésicos
  • Sobre a implementação de métodos de marcha rápida para treliças 3D
  • Multistencils FMM: uma solução altamente precisa para a Equação Eikonal em Domínios Cartesianos

Links úteis: - Propagação frontal em 2D e 3D

Espero que isso ajude um pouco, embora não seja exatamente o estado da arte.

Nomaru
fonte