python 中的二值图像去噪

denoising binary image in python

对于我的项目,我试图在 python 中使用 openCV 对图像进行二值化。我使用 openCV 的自适应高斯阈值来转换图像,结果如下:

我想使用二进制图像进行 OCR,但它太嘈杂了。 python中的二值图像有没有办法去除噪声?我已经从 openCV 尝试过 fastNlMeansDenoising,但它没有什么区别。

P.S 也欢迎更好的二值化选项

你可以试试形态学变换接近去除小"holes"。 首先使用 numpy 定义内核,您可能需要调整大小。选择与噪声一样大的内核大小。

kernel = np.ones((5,5),np.uint8)

然后运行使用内核的morphologyEx。

denoised = cv2.morphologyEx(image, cv2.MORPH_CLOSE, kernel)

如果文本被删除,您可以尝试腐蚀图像,这将 "grow" 黑色像素。如果噪音和数据一样大,这种方法就没用了。

erosion = cv2.erode(img,kernel,iterations = 1)

也可以使用 GraphCuts 来完成此类任务。您将需要安装 maxflow library in order to run the code. I quickly copied the code from their tutorial 并修改它,这样您就可以更轻松地 运行 它。只需使用平滑参数来增加或减少图像的去噪。

import cv2
import numpy as np
import matplotlib.pyplot as plt
import maxflow 

# Important parameter
# Higher values means making the image smoother
smoothing = 110

# Load the image and convert it to grayscale image 
image_path = 'your_image.png'
img = cv2.imread('image_path')
img = cv2.cvtColor(img, cv2.COLOR_BGR2GRAY)
img = 255 * (img > 128).astype(np.uint8)

# Create the graph.
g = maxflow.Graph[int]()
# Add the nodes. nodeids has the identifiers of the nodes in the grid.
nodeids = g.add_grid_nodes(img.shape)
# Add non-terminal edges with the same capacity.
g.add_grid_edges(nodeids, smoothing)
# Add the terminal edges. The image pixels are the capacities
# of the edges from the source node. The inverted image pixels
# are the capacities of the edges to the sink node.
g.add_grid_tedges(nodeids, img, 255-img)

# Find the maximum flow.
g.maxflow()
# Get the segments of the nodes in the grid.
sgm = g.get_grid_segments(nodeids)

# The labels should be 1 where sgm is False and 0 otherwise.
img_denoised = np.logical_not(sgm).astype(np.uint8) * 255

# Show the result.
plt.subplot(121)
plt.imshow(img, cmap='gray')
plt.title('Binary image')
plt.subplot(122)
plt.title('Denoised binary image')
plt.imshow(img_denoised, cmap='gray')
plt.show()

# Save denoised image
cv2.imwrite('img_denoised.png', img_denoised)

Result

您应该首先将参数调整为自适应阈值,使其使用更大的区域。这样它就不会分割出噪音。只要你的输出图像比输入图像有更多的噪声,你就知道你做错了什么。

我建议使用闭合(在输入 grey-value 图像上)和结构元素刚好足以删除所有文本作为自适应阈值。此结果与输入图像之间的差异恰好是所有文本。然后,您可以对此差异应用常规阈值。