我想将扫描图像转换为黑白图像,目标是在通过互联网传输图像之前减小文件大小以进行OCR。
扫描仪/一般图像编辑软件创建的正常二值化/黑白图像会产生不良结果。
留下了很多随机的黑色像素,它们实际上只是来自二值化的噪音,这会导致OCR尝试识别没有的字符,或者在字符后插入句号,冒号等。
我可以在OpenCV中使用什么来对图像进行二值化处理,保留线条,字符和图像。暗区是否牢固,并减少白色区域的像素噪声?
我玩过cvThreshold和cvAdaptiveThreshold,但结果还不是很好。
例如,请查看此original image和desired result。
答案 0 :(得分:2)
您可以试试这个,但仍需要调整一些参数。
#define ALPHA_SCALE 2
#define THRESHOLD_VAL 40
#define MAX_VAL_FOR_THRESHOLD 250
#define PIXEL_MISMATCH_COUNT 10 //9, 7
Mat current_frame_t2;
IplImage *img = cvLoadImage("Original.tiff", CV_LOAD_IMAGE_UNCHANGED );
cvNamedWindow("My_Win", CV_WINDOW_AUTOSIZE);
// namedWindow("My_Win", 1);
cvShowImage("My_Win", img);
cvWaitKey(10);
Mat current_frame_t1(img);
cvtColor(current_frame_t1, current_frame_t2, CV_RGB2GRAY);
current_frame_t1.release();
imshow("My_Win", current_frame_t2);
cvWaitKey(10);
equalizeHist(current_frame_t2, current_frame_t1);
current_frame_t2.release();
convertScaleAbs(current_frame_t1, current_frame_t2,ALPHA_SCALE);
threshold(current_frame_t2, current_frame_t1, THRESHOLD_VAL, MAX_VAL_FOR_THRESHOLD, CV_THRESH_BINARY);
medianBlur(current_frame_t1,current_frame_t2,1);
imshow("My_Win", current_frame_t2);
imwrite("outimg.tiff", current_frame_t2),
cvWaitKey(0);
答案 1 :(得分:1)
您可以使用connected-components labeling算法并删除未在图像中填充合理像素数的组件。
在OpenCV中实现它的一种非常简单的方法是使用轮廓:
1. Do the preliminary bizariztion of the OCR, that will give you a very noise output.
2. Find all contours on that noise image.
3. For each found contour:
3.1. Fill the contour with a color different of the two options in the binarized image.
3.2. Count the ammount of pixels filled with that color.
3.3. If the ammount of pixels are smaller than a given treshold, fill the contour with the void collor of the binary image.
供参考:cv::findContours和cv::drawContours。
可以在3.1上优化循环分类多个轮廓。并且在3.2的所有这些颜色的单次通过中进行像素计数。 。我没有使用优化版本,因为你可能有超过253个不同的组(255种颜色 - 二进制图像的2种默认颜色),并且考虑到这一点并不是那么直接。