title: Removing isolated pixels using OpenCV
body: <p>I'm looking for a way to remove isolated white pixels from a binary image using OpenCV. A similar question (<a href="https://stackoverflow.com/questions/13755840/opencv-get-rid-of-isolated-pixels">OpenCV get rid of isolated pixels</a>) has a bunch of "answers" but none seem to work for me. I've tried various combinations of opening and closing without success as well.</p>
  
  <p>The article here:</p>
  
  <p><a href="https://homepages.inf.ed.ac.uk/rbf/HIPR2/hitmiss.htm" rel="noreferrer">https://homepages.inf.ed.ac.uk/rbf/HIPR2/hitmiss.htm</a></p>
  
  <p>Suggests I can use the hit-or-miss operation for exactly this purpose:</p>
  
  <p><a href="https://i.stack.imgur.com/LNTEt.gif" rel="noreferrer"><img src="https://i.stack.imgur.com/LNTEt.gif" alt="Structuring elements"></a></p>
  
  <blockquote>
    <p><strong>1</strong> is used to locate isolated points in a binary image</p>
  </blockquote>
  
  <p>And that the reason why is that 0s are interpreted differently than when they are used with erosion/dilation directly (where 0s are interpreted as "don't care's" rather than "not white" which is basically what I'm after). However, using this kernel simply renders the original image.</p>
  
  <p>My input image is this:</p>
  
  <p><a href="https://i.stack.imgur.com/3VQT1.png" rel="noreferrer"><img src="https://i.stack.imgur.com/3VQT1.png" alt="Calc input image"></a></p>
  
  <p>You'll notice there's a few white pixels near the left-hand side of the image which I'd like to get rid of.</p>
  
  <p>Here's the code:</p>
  
  <pre><code>kernel = np.array([ [0, 0, 0],
                      [0, 1, 0],
                      [0, 0, 0]],np.uint8)
  
  hitormiss = cv2.morphologyEx(input_image, cv2.MORPH_HITMISS, kernel)
  
  cv2.imshow('hitormiss', hitormiss)
  </code></pre>
  
  <p>What is the right way of removing isolated pixels like these?</p>
  
  <p><strong>Update</strong>: Alexander's answer works like a charm and is the fastest solution. The other answer provides a solution too, which is to use the <a href="http://docs.opencv.org/3.1.0/d3/dc0/group__imgproc__shape.html" rel="noreferrer">cv2.connectedComponents</a> function, but it is much more processor-intensive. Here's a function that uses this approach:</p>
  
  <pre><code>def remove_isolated_pixels(self, image):
      connectivity = 8
  
      output = cv2.connectedComponentsWithStats(image, connectivity, cv2.CV_32S)
  
      num_stats = output[0]
      labels = output[1]
      stats = output[2]
  
      new_image = image.copy()
  
      for label in range(num_stats):
          if stats[label,cv2.CC_STAT_AREA] == 1:
              new_image[labels == label] = 0
  
      return new_image
  </code></pre>