用 Java 和 Tesseract 进行验证码识别
验证码(CAPTCHA)常用于防止机器人滥用网站资源,但在某些自动化测试或数据处理场景中,我们需要自动识别验证码。本文将介绍如何使用 Java + Tesseract OCR 进行验证码解析,并优化识别准确度。
- 环境准备
在开始之前,请确保你的开发环境已安装以下工具:
更多内容访问ttocr.com或联系1436423940
Java 8+
Tesseract OCR
Tess4J(Java 的 Tesseract OCR 封装库)
1.1 安装 Tesseract OCR
根据你的操作系统选择适合的安装方式:
Windows:
从 Tesseract 官方 GitHub
下载并安装。
安装完成后,配置环境变量,将 Tesseract-OCR 目录添加到 PATH。
Linux(Ubuntu 示例):
sudo apt update
sudo apt install tesseract-ocr
macOS(使用 Homebrew):
brew install tesseract
安装完成后,运行以下命令检查 Tesseract 是否可用:
tesseract --version
1.2 添加 Tess4J 依赖
如果使用 Maven,在 pom.xml 中添加:
如果使用 Gradle:
dependencies {
implementation 'net.sourceforge.tess4j:tess4j:4.5.5'
}
- 代码实现:识别验证码
import net.sourceforge.tess4j.ITesseract;
import net.sourceforge.tess4j.Tesseract;
import net.sourceforge.tess4j.TesseractException;
import javax.imageio.ImageIO;
import java.awt.*;
import java.awt.image.BufferedImage;
import java.io.File;
import java.io.IOException;
public class CaptchaRecognizer {
public static void main(String[] args) {
String imagePath = "captcha.png"; // 替换为你的验证码图片路径
try {
// 预处理验证码
File processedImage = preprocessImage(imagePath);
// 进行 OCR 识别
String recognizedText = recognizeCaptcha(processedImage);
System.out.println("识别出的验证码: " + recognizedText);
} catch (IOException | TesseractException e) {
e.printStackTrace();
}
}
// 预处理图像,提高 OCR 识别率
public static File preprocessImage(String imagePath) throws IOException {
BufferedImage image = ImageIO.read(new File(imagePath));
// 转换为灰度图
BufferedImage grayImage = new BufferedImage(image.getWidth(), image.getHeight(), BufferedImage.TYPE_BYTE_GRAY);
Graphics g = grayImage.getGraphics();
g.drawImage(image, 0, 0, null);
g.dispose();
// 二值化处理
for (int x = 0; x < grayImage.getWidth(); x++) {
for (int y = 0; y < grayImage.getHeight(); y++) {
int rgb = grayImage.getRGB(x, y);
int gray = (rgb & 0xFF);
int binary = gray > 128 ? 0xFFFFFF : 0x000000;
grayImage.setRGB(x, y, binary);
}
}
// 保存处理后的图像
File outputFile = new File("processed_captcha.png");
ImageIO.write(grayImage, "png", outputFile);
return outputFile;
}
// 使用 Tesseract 进行 OCR 识别
public static String recognizeCaptcha(File imageFile) throws TesseractException {
ITesseract tesseract = new Tesseract();
// 设置 Tesseract-OCR 的安装路径(Windows 需要手动设置)
tesseract.setDatapath("C:/Program Files/Tesseract-OCR/tessdata"); // 请根据实际路径修改
// 设定识别语言(默认 "eng")
tesseract.setLanguage("eng");
// 设定 PSM(页面分割模式),对于验证码推荐使用 PSM 6(单行文本)
tesseract.setTessVariable("tessedit_pageseg_mode", "6");
return tesseract.doOCR(imageFile);
}
}
- 代码解析
3.1 预处理验证码图像
为了提高 OCR 识别率,我们对验证码图像进行了以下处理:
转换为灰度图:去除颜色干扰,仅保留亮度信息。
二值化处理:将图像转换为黑白,提高字符清晰度,使 OCR 更容易识别。
3.2 OCR 解析
我们使用 Tess4J 作为 Java 的 OCR 解决方案,核心 API 解析:
tesseract.setDatapath("路径"):设置 Tesseract-OCR 的安装路径(Windows 必须手动指定)。
tesseract.setLanguage("eng"):设定识别语言为 英语(验证码通常是数字或英文字母)。
tesseract.setTessVariable("tessedit_pageseg_mode", "6"):设置 页面分割模式,6 适用于验证码识别(假设单行文本)。
tesseract.doOCR(imageFile):执行 OCR 识别,并返回识别出的文本。
- 运行程序
将 captcha.png 放入代码目录下,然后执行:
javac CaptchaRecognizer.java
java CaptchaRecognizer
示例输出:
识别出的验证码: 7YHD2
- 提高 OCR 识别准确率
5.1 选择合适的 Tesseract 语言模型
如果验证码包含大量数字,可以使用 digits.traineddata 进行识别:
tesseract.setLanguage("eng+osd");
Tesseract 默认使用 eng(英语),但可以结合其他训练数据,如:
tesseract.setLanguage("eng+digits");
5.2 进一步优化图像处理
除了灰度化和二值化,可以使用 OpenCV 进行噪声去除,提高识别率:
// 高斯模糊去噪
BufferedImage denoisedImage = new BufferedImage(width, height, BufferedImage.TYPE_BYTE_GRAY);
Graphics2D g2d = denoisedImage.createGraphics();
g2d.drawImage(grayImage, 0, 0, null);
g2d.dispose();
5.3 训练 Tesseract 适应特定验证码
如果 Tesseract 识别率仍然不高,可以训练一个专用的验证码模型:
收集样本:准备 1000+ 张验证码及其文本标签。
使用 Tesseract 训练工具 进行模型训练(参考 官方文档
)。
训练完成后,加载自定义训练数据:
tesseract.setLanguage("custom");
浙公网安备 33010602011771号