Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Removing pixels surrounded by white pixels OpenCV

Tags:

python

opencv

I have a black and white image which has a lot of noise. I would like to remove only black pixels that are completely surrounded by white ones. I tried doing so with Filter2d, but I could not achieve it.

like image 919
Asmastas Maz Avatar asked Oct 29 '25 03:10

Asmastas Maz


2 Answers

I'd use a convolution (again) 1:

>>> import numpy as np
>>> from scipy.signal import convolve2d
>>> 
>>> kernel = np.ones((3,3))
>>> kernel[1,1] = 0
>>> print(kernel)
[[ 1.  1.  1.]
 [ 1.  0.  1.]
 [ 1.  1.  1.]]
>>> # Create a decent test array that shows the features
... test = np.array(
...     [[0,1,1,0,1,1],
...      [1,1,1,1,1,0],
...      [1,0,1,1,0,1],
...      [1,1,1,0,0,0],
...      [1,1,1,0,1,0],
...      [1,1,1,0,0,0]])
>>> 
>>> mask = convolve2d(test, kernel, mode='same', fillvalue=1)
>>> print(mask)
[[ 8.  7.  7.  8.  6.  7.]
 [ 6.  6.  6.  6.  5.  7.]
 [ 7.  8.  6.  5.  4.  4.]
 [ 7.  7.  5.  5.  3.  5.]
 [ 8.  8.  5.  4.  0.  4.]
 [ 8.  8.  6.  6.  4.  6.]]
>>> result = test.copy()
>>> result[np.logical_and(mask==8, test==0)] = 1
>>> print(result)
[[1 1 1 1 1 1]
 [1 1 1 1 1 0]
 [1 1 1 1 0 1]
 [1 1 1 0 0 0]
 [1 1 1 0 1 0]
 [1 1 1 0 0 0]]

As you can see, the result array has changed all "black" pixels (here represented by the value of 0) that were completely surrounded by white (represented by ones) on all 8 sides, even in the corners and on the edges.

Edit: Hugo Rune's answer is better though if you have "pepper" noise, which means you'd have small groups of black pixels that are surrounded by white pixels and not just single pixels. For single pixels, which is how I interpreted your question, the above will work fine.

Footnote:

1: Actually you'd need a correlation, but in this case it is the same, because the kernel is symmetric.

like image 131
Oliver W. Avatar answered Oct 31 '25 15:10

Oliver W.


You have two possibilities:

Perform a morphological closing.

enter image description here

This will remove all single black pixels, but it will also remove some other shapes, such as one-pixel-thick black lines, or sharp black corners

This is the standard approach to remove "pepper-noise", noisy individual black pixels.


The other way, which will remove only lone black pixels:

  • invert the image
  • use findContours to find all connected components in the inverted image
  • select all found contours with an area of 1, and paint them white in the original image

This will however not work if two random black pixels are by chance neighbours, so perhaps paint over all areas of size 2 or 3.

like image 43
HugoRune Avatar answered Oct 31 '25 15:10

HugoRune



Donate For Us

If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!