2014-12-25 2 views
1

Я хочу, чтобы иметь возможность найти длину пути в картине, это может быть длина червя, фигурная человеческие волосы, Амазонка и т.д. Рассмотрим реки Амазонки картину: enter image description hereКак найти длину пути (кривой) на картинке?

I попытался сделать скелет моего изображения после его бинаризации, но проблема в том, что скелеты (полученные двумя методами) имеют много небольших ветвей, что приводит к их площади намного больше, чем приблизительная длина пути. Для этого я использовал scikit-image. Вот код и результаты:

from skimage.filter import threshold_otsu 
from skimage import io 
from skimage.filter.rank import median 
from skimage.morphology import disk,skeletonize,medial_axis,remove_small_objects 
import matplotlib.pyplot as plt 


input_image = io.imread('Amazon-river2.jpg', 
        as_grey=True, plugin=None, flatten=None) 
image = median(input_image, disk(15)) 

thresh = threshold_otsu(image) 
image = image < thresh 

skel1=skeletonize(image) 
skel2=medial_axis(image) 

min_size=sum(sum(skel1))/2 

remove_small_objects(skel1,min_size=min_size,connectivity=5,in_place=True) 

remove_small_objects(skel2,min_size=min_size,connectivity=5,in_place=True) 


fig2, ax = plt.subplots(2, 2, figsize=(24, 12)) 

ax[0,0].imshow(input_image,cmap=plt.cm.gray) 
ax[0,0].set_title('Input image') 
ax[0,0].axis('image') 
ax[0,1].imshow(image, cmap=plt.cm.gray) 
ax[0,1].set_title('Binary image') 
ax[0,1].axis('image') 
ax[1,0].imshow(skel1, cmap=plt.cm.gray) 
ax[1,0].set_title('Skeleton') 
ax[1,0].axis('image') 
ax[1,1].imshow(skel2,cmap=plt.cm.gray) 
ax[1,1].set_title('Sleleton - Medial axis') 
ax[1,1].axis('image') 

plt.show() 


print ("Length 1: {0}".format(sum(sum(skel1)))) 
print ("Length 2: {0}".format(sum(sum(skel2)))) 

enter image description here

Любые предложения, чтобы решить эту проблему? Любая другая идея для измерения длины дуги?

ответ

3

Как я вижу, это график, когда узлы являются конечными точками, и они связаны по пути. поэтому каждая точка может (или нет) подключаться к любой другой точке, и вам нужно найти самый длинный путь.

так что вам нужно найти все конечные точки, начиная с каждой конечной точки начинать итерацию, пока не дойдете до другой конечной точки. после выполнения этого для всех точек вы можете пройти самый длинный путь !!!

надежда, что помогает

+0

Я думал об этом! но это очень сложно сделать, потому что вы должны рассмотреть все те моменты, которые вы приняли решение о том, чтобы идти тем или иным путем, и это похоже на дерево решений. Любая идея, как создать код для этого? – ehsan88

0

Попробуйте следующее

  1. Выполните сегментирование цвета на R или B канала, а RGB-> Серый
  2. Вместо greythresh Оцу, идти вручную установить порог или использования multithresh Otsu (должно быть также в python)
  3. Выполнение следующих операций морфологии перед скелетонизацией на двоичном изображении: Erosion -> Thinning -> Areaopen. Это должно устранить острова.

Хотя у скелетониза всегда будут такие проблемы, вы можете пойти на обнаружение canny edge на двоичном. Выполните следующие на каждом ребре Arc length

0

Полностью согласен с предложением Yaron Kahanovitch «s, и я думаю, что NetworkX должен быть в состоянии сделать работу, чтобы вычислить самую длинную траекторию/маршрута, однако, как автоматически извлекать конечную точку или точку пересечения в качестве узлов и рассчитать расстояние для взвешенного края все еще борется и бросать вызов задачам, которые предстоит выполнить.

В результате я только что разместил another question on stackoverflow и надеюсь, что какой-нибудь выродка может дать нам ценные предложения.

Смежные вопросы