2013-01-17 7 views
5

Próbuję wypełnić dziury w obrazie binarnym. Obraz jest dość duży, więc podzieliłem go na kawałki w celu przetworzenia.Scipy Binary Closing - Edge Pixels tracą wartość

Podczas korzystania z funkcji scipy.ndimage.morphology.binary_fill_holes wypełnia większe dziury, które należą do obrazu. Tak więc próbowałem użyć scipy.ndimage.morphology.binary_closing, która dała pożądane rezultaty wypełniania małych dziur w obrazie. Jednakże, gdy scalam kawałki razem, aby utworzyć cały obraz, kończę z liniami szwu, ponieważ funkcja binary_closing usuwa wszelkie wartości z pikseli granicznych każdej porcji.

Czy istnieje sposób na uniknięcie tego efektu?

+0

Po pierwsze, byłoby dobrze, gdybyś mógł dodać trochę więcej obrazu lub kodu wyjaśniającego twój problem. Po drugie, nie można uniknąć wprowadzania artefaktów przez cięcie w ten sposób, będziesz musieć/poszerzać plasterki o wielkość elementu strukturyzującego, aby wynik był poprawny. – YXD

+0

Właściwy sposób to zrobić za pomocą morfologii rekonstrukcja z zamkniętym obrazem jako znacznikiem. – mmgp

Odpowiedz

1

Operacje obejmujące informacje z sąsiednich pikseli, takie jak closing, zawsze będą mieć problemy z krawędziami. W twoim przypadku jest to bardzo łatwe do pokonania: po prostu przetwarzaj podobrazi, które są nieco większe niż twoje kafelki, i zachowaj dobre części, gdy łączą się ze sobą.

+0

Po prostu spróbowałem czegoś nowego, co według mnie brzmi podobnie do tego, co sugerujesz. Wziąłem moją porcję i dodałem rząd zer na górze i na dole tablicy używając vstack. Zrobiłem to samo na lewo i na prawo, używając hstack. Następnie przetworzyłem zamknięcie binarne. W końcu usunąłem zewnętrzne wiersze i kolumny, aby przywrócić oryginalny rozmiar obrazu. Z tego co mogę powiedzieć, kiedy kreślę obrazy obok siebie. Wygląda to poprawnie. – Brian

+1

To może zadziałać, ale myślę, że jest mniej dokładne niż użycie rzeczywistych danych z obrazu.Chodzi mi o to, że jeśli Twój obraz ma powiedzmy 1Mx1M i chcesz to zrobić w 100 podobrazach 100Kx100K, to zamiast tego przetwarzaj podobrazi, które są rozmieszczone w 100-krotnym rozmiarze, ale są 100 200 x 100 200 (tj. Mają 100-pikselowe wypełnienie rzeczywistych i dokładne dane z obrazu dookoła), a po ponownym złożeniu wystarczy użyć dobrych części centralnych, które mają 100 000 x 100 000. – tom10

4

Tak.

  1. Oznacz swoje zdjęcie za pomocą ndimage.label (najpierw odwróć obraz, otwory = czarne).
  2. Znajdź plastry obiektów dziura z ndimage.find_objects
  3. filtrować listę plastry obiektu w oparciu o kryteria wielkości
  4. odwracających cofających obrazu i wykonać binary_fill_holes na plasterki, które spełniają podane kryteria.

To powinno wystarczyć, bez potrzeby przycinania obrazu. Na przykład: image

Wejście:

enter image description here

wyjścia obrazu (otwory Bliski rozmiar odeszły):

enter image description here

Oto kod (nierówność jest ustawione, aby usunąć środek rozmiar blobs):

import scipy 
from scipy import ndimage 
import numpy as np 

im = scipy.misc.imread('cheese.png',flatten=1) 
invert_im = np.where(im == 0, 1, 0) 
label_im, num = ndimage.label(invert_im) 
holes = ndimage.find_objects(label_im) 
small_holes = [hole for hole in holes if 500 < im[hole].size < 1000] 
for hole in small_holes: 
    a,b,c,d = (max(hole[0].start-1,0), 
       min(hole[0].stop+1,im.shape[0]-1), 
       max(hole[1].start-1,0), 
       min(hole[1].stop+1,im.shape[1]-1)) 
    im[a:b,c:d] = scipy.ndimage.morphology.binary_fill_holes(im[a:b,c:d]).astype(int)*255 

Należy również zauważyć, że musiałem zwiększyć rozmiar plasterków, tak aby otwory były obramowane dookoła.

+0

Mam problem ze znalezieniem jakiejkolwiek różnicy między dwoma opublikowanymi obrazami. – Jaime

+0

@Jaime - przyjrzyj się uważniej;) otwory o średnich rozmiarach są nieobecne na drugim obrazie. – fraxel

+0

Moja zła! Szukałem malusieńkich dziur, które zniknęły, są znacznie większe, niż się spodziewałem, – Jaime