`

Java OCR tesseract 图像智能字符识别技术 Java代码实现

阅读更多

接着上一篇OCR所说的,上一篇给大家介绍了tesseract 在命令行的简单用法,当然了要继承到我们的程序中,还是需要代码实现的,下面给大家分享下Java实现的例子。

拿代码扫描上面的图片,然后输出结果。主要思想就是利用Java调用系统任务。

下面是核心代码:

package com.zhy.test;  
  
import java.io.BufferedReader;  
  
import java.io.File;  
import java.io.FileInputStream;  
import java.io.InputStreamReader;  
import java.util.ArrayList;  
import java.util.List;  
  
import org.jdesktop.swingx.util.OS;  
  
public class OCRHelper  
{  
    private final String LANG_OPTION = "-l";  
    private final String EOL = System.getProperty("line.separator");  
    /** 
     * 文件位置我防止在,项目同一路径 
     */  
    private String tessPath = new File("tesseract").getAbsolutePath();  
  
    /** 
     * @param imageFile 
     *            传入的图像文件 
     * @param imageFormat 
     *            传入的图像格式 
     * @return 识别后的字符串 
     */  
    public String recognizeText(File imageFile) throws Exception  
    {  
        /** 
         * 设置输出文件的保存的文件目录 
         */  
        File outputFile = new File(imageFile.getParentFile(), "output");  
  
        StringBuffer strB = new StringBuffer();  
        List<String> cmd = new ArrayList<String>();  
        if (OS.isWindowsXP())  
        {  
            cmd.add(tessPath + "\\tesseract");  
        } else if (OS.isLinux())  
        {  
            cmd.add("tesseract");  
        } else  
        {  
            cmd.add(tessPath + "\\tesseract");  
        }  
        cmd.add("");  
        cmd.add(outputFile.getName());  
        cmd.add(LANG_OPTION);  
//      cmd.add("chi_sim");  
        cmd.add("eng");  
  
        ProcessBuilder pb = new ProcessBuilder();  
        /** 
         *Sets this process builder's working directory. 
         */  
        pb.directory(imageFile.getParentFile());  
        cmd.set(1, imageFile.getName());  
        pb.command(cmd);  
        pb.redirectErrorStream(true);  
        Process process = pb.start();  
        // tesseract.exe 1.jpg 1 -l chi_sim  
        // Runtime.getRuntime().exec("tesseract.exe 1.jpg 1 -l chi_sim");  
        /** 
         * the exit value of the process. By convention, 0 indicates normal 
         * termination. 
         */  
//      System.out.println(cmd.toString());  
        int w = process.waitFor();  
        if (w == 0)// 0代表正常退出  
        {  
            BufferedReader in = new BufferedReader(new InputStreamReader(  
                    new FileInputStream(outputFile.getAbsolutePath() + ".txt"),  
                    "UTF-8"));  
            String str;  
  
            while ((str = in.readLine()) != null)  
            {  
                strB.append(str).append(EOL);  
            }  
            in.close();  
        } else  
        {  
            String msg;  
            switch (w)  
            {  
            case 1:  
                msg = "Errors accessing files. There may be spaces in your image's filename.";  
                break;  
            case 29:  
                msg = "Cannot recognize the image or its selected region.";  
                break;  
            case 31:  
                msg = "Unsupported image format.";  
                break;  
            default:  
                msg = "Errors occurred.";  
            }  
            throw new RuntimeException(msg);  
        }  
        new File(outputFile.getAbsolutePath() + ".txt").delete();  
        return strB.toString().replaceAll("\\s*", "");  
    }  
}  

 代码很简单,中间那部分ProcessBuilder其实就类似Runtime.getRuntime().exec("tesseract.exe 1.jpg 1 -l chi_sim"),大家不习惯的可以使用Runtime。

 

测试代码:

package com.zhy.test;  
  
import java.io.File;  
  
public class Test  
{  
    public static void main(String[] args)  
    {  
        try  
        {  
              
            File testDataDir = new File("testdata");  
            System.out.println(testDataDir.listFiles().length);  
            int i = 0 ;   
            for(File file :testDataDir.listFiles())  
            {  
                i++ ;  
                String recognizeText = new OCRHelper().recognizeText(file);  
                System.out.print(recognizeText+"\t");  
  
                if( i % 5  == 0 )  
                {  
                    System.out.println();  
                }  
            }  
              
        } catch (Exception e)  
        {  
            e.printStackTrace();  
        }  
  
    }  
}  

 
输出结果:

 

对比第一张图片,是不是很完美~哈哈 ,当然了如果你只需要实现验证码的读写,那么上面就足够了。下面继续普及图像处理的知识。



-------------------------------------------------------------------我的分割线--------------------------------------------------------------------

当然了,有时候图片被扭曲或者模糊的很厉害,很不容易识别,所以下面我给大家介绍一个去噪的辅助类,绝对碉堡了,先看下效果图。

来张特写:

一个类,不依赖任何jar,把图像中的干扰线消灭了,是不是很给力,然后再拿这样的图片去识别,会不会效果更好呢,嘿嘿,大家自己实验~

代码:

package com.zhy.test;  
  
import java.awt.Color;  
import java.awt.image.BufferedImage;  
import java.io.File;  
import java.io.IOException;  
  
import javax.imageio.ImageIO;  
  
public class ClearImageHelper  
{  
  
    public static void main(String[] args) throws IOException  
    {  
  
          
        File testDataDir = new File("testdata");  
        final String destDir = testDataDir.getAbsolutePath()+"/tmp";  
        for (File file : testDataDir.listFiles())  
        {  
            cleanImage(file, destDir);  
        }  
  
    }  
  
    /** 
     *  
     * @param sfile 
     *            需要去噪的图像 
     * @param destDir 
     *            去噪后的图像保存地址 
     * @throws IOException 
     */  
    public static void cleanImage(File sfile, String destDir)  
            throws IOException  
    {  
        File destF = new File(destDir);  
        if (!destF.exists())  
        {  
            destF.mkdirs();  
        }  
  
        BufferedImage bufferedImage = ImageIO.read(sfile);  
        int h = bufferedImage.getHeight();  
        int w = bufferedImage.getWidth();  
  
        // 灰度化  
        int[][] gray = new int[w][h];  
        for (int x = 0; x < w; x++)  
        {  
            for (int y = 0; y < h; y++)  
            {  
                int argb = bufferedImage.getRGB(x, y);  
                // 图像加亮(调整亮度识别率非常高)  
                int r = (int) (((argb >> 16) & 0xFF) * 1.1 + 30);  
                int g = (int) (((argb >> 8) & 0xFF) * 1.1 + 30);  
                int b = (int) (((argb >> 0) & 0xFF) * 1.1 + 30);  
                if (r >= 255)  
                {  
                    r = 255;  
                }  
                if (g >= 255)  
                {  
                    g = 255;  
                }  
                if (b >= 255)  
                {  
                    b = 255;  
                }  
                gray[x][y] = (int) Math  
                        .pow((Math.pow(r, 2.2) * 0.2973 + Math.pow(g, 2.2)  
                                * 0.6274 + Math.pow(b, 2.2) * 0.0753), 1 / 2.2);  
            }  
        }  
  
        // 二值化  
        int threshold = ostu(gray, w, h);  
        BufferedImage binaryBufferedImage = new BufferedImage(w, h,  
                BufferedImage.TYPE_BYTE_BINARY);  
        for (int x = 0; x < w; x++)  
        {  
            for (int y = 0; y < h; y++)  
            {  
                if (gray[x][y] > threshold)  
                {  
                    gray[x][y] |= 0x00FFFF;  
                } else  
                {  
                    gray[x][y] &= 0xFF0000;  
                }  
                binaryBufferedImage.setRGB(x, y, gray[x][y]);  
            }  
        }  
  
        // 矩阵打印  
        for (int y = 0; y < h; y++)  
        {  
            for (int x = 0; x < w; x++)  
            {  
                if (isBlack(binaryBufferedImage.getRGB(x, y)))  
                {  
                    System.out.print("*");  
                } else  
                {  
                    System.out.print(" ");  
                }  
            }  
            System.out.println();  
        }  
  
        ImageIO.write(binaryBufferedImage, "jpg", new File(destDir, sfile  
                .getName()));  
    }  
  
    public static boolean isBlack(int colorInt)  
    {  
        Color color = new Color(colorInt);  
        if (color.getRed() + color.getGreen() + color.getBlue() <= 300)  
        {  
            return true;  
        }  
        return false;  
    }  
  
    public static boolean isWhite(int colorInt)  
    {  
        Color color = new Color(colorInt);  
        if (color.getRed() + color.getGreen() + color.getBlue() > 300)  
        {  
            return true;  
        }  
        return false;  
    }  
  
    public static int isBlackOrWhite(int colorInt)  
    {  
        if (getColorBright(colorInt) < 30 || getColorBright(colorInt) > 730)  
        {  
            return 1;  
        }  
        return 0;  
    }  
  
    public static int getColorBright(int colorInt)  
    {  
        Color color = new Color(colorInt);  
        return color.getRed() + color.getGreen() + color.getBlue();  
    }  
  
    public static int ostu(int[][] gray, int w, int h)  
    {  
        int[] histData = new int[w * h];  
        // Calculate histogram  
        for (int x = 0; x < w; x++)  
        {  
            for (int y = 0; y < h; y++)  
            {  
                int red = 0xFF & gray[x][y];  
                histData[red]++;  
            }  
        }  
  
        // Total number of pixels  
        int total = w * h;  
  
        float sum = 0;  
        for (int t = 0; t < 256; t++)  
            sum += t * histData[t];  
  
        float sumB = 0;  
        int wB = 0;  
        int wF = 0;  
  
        float varMax = 0;  
        int threshold = 0;  
  
        for (int t = 0; t < 256; t++)  
        {  
            wB += histData[t]; // Weight Background  
            if (wB == 0)  
                continue;  
  
            wF = total - wB; // Weight Foreground  
            if (wF == 0)  
                break;  
  
            sumB += (float) (t * histData[t]);  
  
            float mB = sumB / wB; // Mean Background  
            float mF = (sum - sumB) / wF; // Mean Foreground  
  
            // Calculate Between Class Variance  
            float varBetween = (float) wB * (float) wF * (mB - mF) * (mB - mF);  
  
            // Check if new maximum found  
            if (varBetween > varMax)  
            {  
                varMax = varBetween;  
                threshold = t;  
            }  
        }  
  
        return threshold;  
    }  
}  

源地址 http://blog.csdn.net/lmj623565791/article/details/23960391/

分享到:
评论

相关推荐

    Java OCR 图像智能字符识别技术,可识别中文

    在Java环境中,我们可以利用Java的JNI(Java Native Interface)技术,调用C++编写的OCR库,如OpenCV和Tesseract的C++接口,实现高效的图像处理和字符识别功能。 总的来说,Java OCR中文字符识别技术结合了图像处理...

    Java OCR tesseract 图像智能文字字符识别技术实例代码

    Java OCR tesseract 图像智能文字字符识别技术是指使用 Java 语言调用 tesseract 图像识别引擎来实现图像智能文字字符识别的技术。该技术可以将图像中的文字识别出来,并将其输出为文本形式。 在该技术实例代码中,...

    Tesseract 图像智能字符识别技术,可识别中文

    **Tesseract:强大的开源OCR...通过以上步骤,你可以利用Eclipse和Java,结合Tesseract OCR引擎,实现对中文图像的智能字符识别。在实际应用中,结合图像处理技术和深度学习方法,可以进一步提升识别的准确性和效率。

    Java OCR 图像智能字符识别-文字识别Demo

    在这个"Java OCR 图像智能字符识别-文字识别Demo"项目中,我们看到的是一个利用Java实现的OCR系统,特别强调了其对中文字符的识别能力。 这个Demo的核心可能包含以下几个关键知识点: 1. **Tesseract OCR引擎**:...

    java OCR 图像智能字符识别技术map.7z

    Java OCR(Optical Character Recognition,光学字符识别)技术是一种用于将图像中的文本转换为机器可编辑格式的方法。在Java中实现OCR技术,开发者可以利用现有的库或者开发自定义解决方案来处理图像并识别其中的...

    Java+OpenCV+OCR 图像字符处理

    接着,OCR是图像字符识别的关键。OCR技术通过分析图像中的形状和结构,将图像中的字符转化为可编辑的文本。这里可能涉及到Tesseract OCR,一个由Google维护的开源OCR引擎。在Java中,我们可以使用Tesseract的Java...

    tesseract-ocr实现图片识别功能(java)

    一个Google支持的开源的OCR图文识别开源项目。去持多语言(当前3.02 版本支持包括英文,简体中文,繁体中文),支持...可以参考网上的相关资料进行对Tesseract字符识别进行样本训练,通过使用训练后的语言库会提高识别精度。

    java实现Tesseract-OCR示例

    Java实现Tesseract-OCR示例主要涉及的是利用Tesseract OCR(Optical Character Recognition,光学字符识别)库进行文字识别的技术。Tesseract是一个开源的OCR引擎,最初由HP开发,后来被Google接手并维护,它能识别...

    tesseract-ocr 字符识别总结

    在使用 Tesseract-OCR 进行字符识别时,需要将图像文件转换为 TIF 格式,然后使用 Tesseract-OCR 进行识别。Tesseract-OCR 会生成一个 lang.box 文件,包含了识别结果。 Tesseract-OCR 是一个功能强大且灵活的 OCR ...

    Java调用OCR进行图片识别

    Tesseract-OCR是一个开源的OCR(Optical Character Recognition,光学字符识别)引擎,由Google开发和维护。它可以将图像转换为文本,支持多种语言和字体。 二、Java调用Tesseract-OCR 要使用Java调用Tesseract-...

    Tesseract_OCR字符识别模块_

    **Tesseract OCR字符识别模块详解** Tesseract OCR(Optical Character Recognition,光学字符识别)是一种开源的、强大的字符识别引擎,由HP公司在1985年开发,后由Google维护和改进。它能够从图像中识别出文本,...

    基于tesseract的多线程OCR服务器的JAVA实现

    在信息技术领域,光学字符识别(OCR)技术被广泛应用于将图像中的文本转换为可编辑的电子格式。Tesseract是一款开源OCR引擎,由Google维护,它具有高精度和强大的语言支持。本项目是将Tesseract与Java相结合,构建了...

    Tesseract-OCR java版

    **Tesseract OCR Java版**是将开源的Tesseract光学字符识别(OCR)引擎与Java环境相结合,用于在图像中识别和提取文字。Tesseract最初由HP开发,后来由Google维护,它具有高度的准确性和可扩展性,尤其适用于处理...

    JavaOcr图像文字识别工具

    Java OCR(Optical Character Recognition,光学字符识别)是一种技术,用于将扫描的文档、图片或PDF中的文本转换为机器可编辑的数据。这项技术在许多领域都有广泛应用,如文档数字化、表格提取、发票处理等。Java ...

    Tesseract OCR图像识别类库 v5.3.4.zip

    Tesseract OCR(Optical Character Recognition,光学字符识别)是一个开源的图像识别引擎,最初由HP公司开发,并在2005年被Google接管并持续维护。Tesseract OCR库以其高效和高准确性的文字识别能力而闻名,适用于...

    使用Java开发的OCR程序 根据图像识别转换成中文

    在IT行业中,OCR(Optical Character Recognition,光学字符识别)技术是一种广泛应用的技术,它能够将图像中的文字识别并转换为可编辑的文本格式。在这个Java开发的OCR程序中,我们聚焦于如何使用Java来实现这一...

    OCR 字符识别_java

    "OCR 字符识别_java"这个主题聚焦于如何在Java项目中集成OCR技术,以实现对图像中的字符进行自动检测和识别。 首先,我们需要了解OCR的基本工作原理。OCR系统通常包括图像预处理、字符分割、特征提取和分类识别四个...

    Java实现ocr图片识别(PaddleOCR)飞桨

    在IT行业中,OCR(Optical Character Recognition,光学字符识别)技术是将图像中的文本转换为机器编码文本的重要工具。在本项目中,我们将探讨如何利用Java集成PaddleOCR,一个由飞桨(PaddlePaddle)框架支持的...

Global site tag (gtag.js) - Google Analytics