【Lecture 5.2】The (Py)Tesseract Library

2023-05-16

文章目录

    • Lecture: The (Py)Tesseract Library
      • 对文本图像的处理
        • 改变图片大小
        • greyscale - 灰度图
        • binarization 二值图
    • Tesseract and Photographs 对图像的OCR识别
    • Jupyter Widgets (Optional)

Lecture: The (Py)Tesseract Library

让我们首先使用 import PIL 库并展示 text图像

from PIL import Image

image = Image.open('readonly/text.png')
display(image)

image-20200604221358198

让我们import pytesseract 库,并使用 dir() 函数看看这个库的一些函数

import pytesseract
dir(pytesseract)
---
['Output',
 'TesseractError',
 '__builtins__',
 '__cached__',
 '__doc__',
 '__file__',
 '__loader__',
 '__name__',
 '__package__',
 '__path__',
 '__spec__',
 'get_tesseract_version',
 'image_to_boxes',
 'image_to_data',
 'image_to_osd',
 'image_to_pdf_or_hocr',
 'image_to_string',
 'pytesseract']

只有少量的函数,我觉得image_to_string 是合适的,我们使用 help() 查看一下

help(pytesseract.image_to_string)
---
Help on function image_to_string in module pytesseract.pytesseract:

image_to_string(image, lang=None, config='', nice=0, output_type='string')
    Returns the result of a Tesseract OCR run on the provided image to string

可见这个函数第一个输入参数是 an image, 剩下的是一些可选参数,返回的是OCR的结果。

这是因为pytesseract库下面正在调用C++库,该库完成了所有艰苦的工作,而作者只是将所有调用传递给了底层tesseract可执行文件。 在使用python库时,这是一个常见问题,这意味着我们需要执行一些 Web 搜索,以便了解如何与tesseract进行交互。

还有一个问题是没有说明输入参数 image 具体是什么,Is it a string to an image file? A PILLOW image?Something else? 我们通过查看源码了解到是一个 PILLOW image。因此输入一个 PIL image是可以作为这个函数的参数的。

为这个函数撰写说明文档

Hint: The doc line we needed was :param image: A PIL Image.Image file or an ndarray of bytes

Ok, lets try and run tesseract on this image

from PIL import Image

image = Image.open('readonly/text.png')  # 代开文件为PILLOW image
display(image)

text = pytesseract.image_to_string(image)
print(text)
# 输出结果
Behold, the magic of OCR! Using
pytesseract, we’ll be able to read the
contents of this image and convert it to
text

More Tesseract - 更复杂的情况

前面我们使用的是清晰的 unambiguous 图片。现在我们试试混淆的图片

from PIL import Image
img = Image.open('readonly/Nosiy_OCR.PNG')
display(img)

image-20200604221323732

现在我们尝试使用 tsseract -OCR 函数

import pytesseract
text = pytesseract.image_to_string(Image.open('readonly/Noisy_OCR.PNG'))
print(text)
# 输出结果
e magic of OCR! Using pytesseract,
le to read the contents of this

 

d convert it to text

识别的不是很好,我们现在采用一种方法:change the size of the image

对文本图像的处理

改变图片大小

import PIL
# 设置图片的 basewidth
basewidth = 600

img = Image.open('readonly/Noisy_OCR.PNG')
# 对图片的比例 ratio 保持不变,我们使用basewidth除以实际的width
wpercent = (basewidth / float(image.size[0]))
# 则设置后的图片高度等于 实际高度乘以这个比例
hsize = int(float(img.size[1]) * float(wpercent))
# 最后,让我们调整图像大小。 抗锯齿 antialiasing是一种调整线条大小以使其平滑的特定方法
img = img.resize((basewidth, hsize), PIL.Image.ANTIALIAS)

# 另存为,展示
img.save('resized_noise.png')
display(img)
# and run OCR
text = pytesseract.image_to_string(Image.open('resized_nois.png')) 
print(text)
e magic of OCR! Using pytesseract,
le to read the contents of this
d convert it to text

通过 resize 图片大小OCR的效果没有提升,下面我们把图像转为灰度图。

greyscale - 灰度图

我们看 PILLOW documention可以发现一种最简单的转换成灰度图的方法是使用 convert() 函数。

img = Image.open('readonly/Noisy_OCR.png')
img = img.convert('L')
---
# Now lets save that image
img.save('greyscale_noise.jpg')
# And run OCR on the greyscale image
text = pytesseract.image_to_string(Image.open('greyscale_noise.jpg')) 
print(text)
# 输出结果
Behold, the magic of OCR! Using pytesseract,
we'll be able to read the contents of this
image and convert it to text

运行效果非常好。

binarization 二值图

这意味着要分为两个不同的部分-在这种情况下为黑色和白色。 二值化通过称为阈值threshold的过程进行。 如果像素值大于阈值,它将被转换为黑色像素; 如果它低于阈值,它将被转换为白色像素。

在 PILLOW 里调用函数:

img = Image.open('readonly/Noisy_OCR.PNG').convert('1')
img.save('black_white_noise.jpg')
display(img)

image-20200604222044753

不过你也可以自己写二值化图像的函数:

def binarize(image_to_transform, threshold):
    # 先转换成单通道的灰度图
 	output_image=image_to_transform.convert("L")
 
 	for x in range(output_image.width):
     	for y in range(output_image.height):
         	# 比较每一个像素
         	if output_image.getpixel((x,y))< threshold: #注意这个函数的参数是一个元组(坐标)
             	output_image.putpixel( (x,y), 0 )
         	else:
             	output_image.putpixel( (x,y), 255 )
 	#now we just return the new image
    return output_image

让我们在不同阈值范围内测试此功能。 请记住,您可以使用 range() 函数生成不同步长的数字列表。 使用开始,停止和步长调用 range()。 因此,让我们尝试 range(0,257,64),它应该生成5个不同阈值的图像

for thresh in range(0,257,64):
    print("Trying with threshold " + str(thresh))
 	# Lets display the binarized image inline
 	display(binarize(Image.open('readonly/Noisy_OCR.PNG'), thresh))
 	# And lets use tesseract on it. It's inefficient to binarize it twice but this is just for
 	# a demo
 	print(pytesseract.image_to_string(binarize(Image.open('readonly/Noisy_OCR.PNG'), thresh)))

Tesseract and Photographs 对图像的OCR识别

让我们尝试一下其它的图片OCR识别,例如一个门头:

from PIL import Image
import pytesseract

image = Image.open('readonly/storefront.jpg')
display(image)
# ocr
pytesseract.image_tostring(image) # 这个方法的对象是 PIL image

image-20200604222759084

''

OCR识别返回空的字符串,说明 Tesseract不能识别这幅图。我们在上一节学习过 裁剪图片的方法,crop the images;我们在这里尝试对原图进行裁剪。

# First, lets set the bounding box. In this image the store name is in a box
# bounded by (315, 170, 700, 270)
bounding_box = (315, 170, 700, 270)
# 对image进行裁剪
title_image=image.crop(bounding_box)

# 展示裁剪后的图片并对其进行OCR识别
display(titlr_image)
pytesseract.image_to_string(title_image)

image-20200612145308979

'FOSSIL'

太好了,我们看到了如何通过减少一些问题来使该工作得以实现。 因此,现在我们已经能够拍摄图像,对其进行预处理(灰度图,二值化,裁剪),以至于希望看到文本,然后将其转换为python可以理解的字符串。

观察图片可以发现墙上也有 商店的名字的标志。我们现在试试能不能识别它。

# 首先我们 determine a bounding box来裁切这个小的标志
bounding_box = (900, 420, 940, 445)
little_sign = image.crop((990, 420, 940, 445))
display(little_sign)

image-20200604223005142

这是一个很小的图片,我们首先对它 resize

# 放大十倍
new_size = (little_sign.width*10, little_sign.height*10)
# Now lets check the docs for resize()
help(little_sign.resize)
---
Help on method resize in module PIL.Image:

resize(size, resample=0, box=None) method of PIL.Image.Image instance
    Returns a resized copy of this image.
    
    :param size: The requested size in pixels, as a 2-tuple:
       (width, height).
    :param resample: An optional resampling filter.  This can be
       one of :py:attr:`PIL.Image.NEAREST`, :py:attr:`PIL.Image.BOX`,
       :py:attr:`PIL.Image.BILINEAR`, :py:attr:`PIL.Image.HAMMING`,
       :py:attr:`PIL.Image.BICUBIC` or :py:attr:`PIL.Image.LANCZOS`.
       If omitted, or if the image has mode "1" or "P", it is
       set :py:attr:`PIL.Image.NEAREST`.
       See: :ref:`concept-filters`.
    :param box: An optional 4-tuple of floats giving the region
       of the source image which should be scaled.
       The values should be within (0, 0, width, height) rectangle.
       If omitted or None, the entire source is used.
    :returns: An :py:class:`~PIL.Image.Image` object.
# 我们可以看到在 resize 的时候可以选用不同的 filters 对图像进行处理,我们选用 Image.NEAREST 试试看
display(little_sign.resize(new_size, Image.NEAREST))
image-20200604223225279

上面是对图像进行resize操作时默认的 filter,让我们看看所有的filter 的效果

options=[Image.NEAREST, Image.BOX, Image.BILINEAR, Image.HAMMING, Image.BICUBIC, Image.LANCZOS]
for option in options:
    # lets print the option name
    print(option)
    # lets display what this option looks like on our little sign
    display(little_sign.resize(new_size, option))

在这种情况下,Image.LANCZOS和Image.BICUBIC筛选器可以很好地完成工作。 让我们看看我们是否能够从调整后的图像中识别出文字

new_size = (little_sign.width*10, little_sign.height*10)
bigger_sign = little_sign.resize(new_size, Image.BICUBIC)
# ocr输出
pytesseract.image_to_string(bigger_sign)
''

并没有识别,

我们再对它尝试二值化 binarize,我么前面编写的二值化程序:

def binarize(image_to_transform, threshold):
    output_image=image_to_transform.convert("L")
    for x in range(output_image.width):
        for y in range(output_image.height):
            if output_image.getpixel((x,y))< threshold:
                output_image.putpixel( (x,y), 0 )
            else:
                output_image.putpixel( (x,y), 255 )
    return output_image

# Now, lets apply binarizations with, say, a threshold of 190, and try and display that
# as well as do the OCR work
binarized_bigger_sign = binarize(bigger_sign, 190)
dispay(binarized_bigger_sign)
pytesseract.image_to_string(binarized_bigger_sign)

image-20200604223537291

'Lae'

好的,该文本几乎没有用。我们应该如何选择最佳的二值化方法来使用? 好的,让我们尝试一些非常简单的方法, 我们正在尝试检测一个英文单词“ FOSSIL”。 如果我们尝试从0到255的所有二值化,并查看列表中是否有英文单词,这可能是一种方法。 因此,让我们看看是否可以编写例程来执行此操作。

# 首先加载英语字符的list 26个英语字母,存放在事先准备的地址
eng_dict=[]
with open ("readonly/words_alpha.txt", "r") as f:
    data=f.read()
    # now we want to split this into a list based on the new line characters
    eng_dict = data.split("\n")  # 将字符串分成一个列表

# 现在,让其遍历所有可能的阈值并寻找英文单词,如果存在则将其打印出来
for i in range(150,170):
    # 让我们将其二值化并将其转换为string值 命名为 strng
    strng = pytesseract.image_to_string(binarize(bigger_sign,i))
    # 我们要从文本中删除非字母字符,例如([%$]),这是首先执行的一种简短方法,让我们仅将字符串转换为小写
    strng=strng.lower()
    # then lets import the string package - it has a nice list of lower case letters
    import string
    # 现在让我们遍历字符串,逐个字符地查看它,并将其放入比较text中
    comparison=''
    for character in strng:
        if character in string.ascii_lowercase: # 是符串类型的话
            comparison = comparison + character
    # 最后,让我们在字典文件中搜索比较
    if comparison in eng_dict:
        # and print it if we find it
        print(comparison)
fossil
si
fossil
fossil
gas
gas
sl
sl
sil

好吧,这并不完美,但是我们看到 fossil 在字典中还有其他值。 这不是清除OCR数据的好方法。 在实践中使用语言或领域特定的词典可能很有用,尤其是在生成针对特定语言(例如医学知识库或位置)的搜索引擎时。

至此,您已经了解了如何处理图像并将其转换为文本。 在本课程的下一个模块中,我们将更深入地研究计算机视觉库,该库可让我们检测其他事物。 然后,继续进行最终的项目!

Jupyter Widgets (Optional)

在这个简短的演讲中,我想向您介绍Jupyter笔记本开发环境中称为小部件Widgets 的更高级功能之一。 有时您想与已创建的函数进行交互,并使用不同的参数多次调用它。 例如,如果我们想在图像的一部分周围绘制一个红色框,以尝试微调裁剪位置。 小部件是在浏览器中快速完成此操作的一种方法,而无需学习如何编写大型桌面应用程序。

让我们来看看。 首先,我们要从PILLOW包中导入Image和ImageDraw类

from PIL import Image, ImageDraw

# 然后导入 interact class from the widgts package
from ipywidgets import interact
# 我们将使用交互来注释函数

image = Image.open('readonly/storefront.jpg')

好的,我们的设置完成了。 现在,我们将使用交互装饰器interact decorator来表示要包装wrap的python函数。 我们使用 @ 符号进行此操作。

这将使用一组与要调用的函数相同的参数。 然后Jupyter将在屏幕上绘制一些滑块,让我们操纵这些值。

Decorators, which is what the @ sign is describing, are standard python statements and just a short hand for functions which wrap other functions. @ 符号描述的装饰器是标准的python语句,只是包装其他函数的函数的简写形式。 不过,它们有点先进,因此我们在本课程中没有讨论它们.

@interact(left=100, top=100, right=200, bottom=200)

def draw_border(left, top, right, bottom):
    img = img.copy()
    drawing_object = ImageDraw.Draw(img)
    drawing_object.rectangle((left, top, right, bottom), fill=None, outline='red')
    display(img)

image-20200604224147701

Jupyter小部件无疑是高级领域,但是如果您想探索更多内容,则可以阅读此处的信息:https://ipywidgets.readthedocs.io/en/stable/examples/Using%20Interact.html

本文内容由网友自发贡献,版权归原作者所有,本站不承担相应法律责任。如您发现有涉嫌抄袭侵权的内容,请联系:hwhale#tublm.com(使用前将#替换为@)

【Lecture 5.2】The (Py)Tesseract Library 的相关文章

  • “language_model_penalty_non_dict_word”在 tesseract 3.01 中没有效果

    我正在设置language model penalty non dict word通过 Tesseract 3 01 的配置文件 但其值没有任何效果 我尝试过使用多个图像及其多个值 但每个图像的输出始终相同 另一位用户也注意到了同样的情况在
  • 使用 OpenCV 和 Tesseract 的摩洛哥车牌识别 (LPR)

    我正在开展一个关于识别摩洛哥车牌的项目 如下图所示 摩洛哥车牌 请问我如何使用 OpenCV 切出车牌并使用 Tesseract 读取中间的数字和阿拉伯字母 我研究过这篇研究论文 https www researchgate net pub
  • Tesseract 虚假空间识别

    我正在使用 tesseract 来识别序列号 这是可以接受的 存在常见问题 例如错误识别零和 O 6 和 5 或 M 和 H 除此之外 这个超正方体还向识别的单词添加了空格 而图像中没有空格 下图被识别为 HI 3H 这张图片的结果是 FB
  • 训练 Tesseract 特定单词 - 可能吗?

    我想使用 Tesseract 从文档中提取大约 10 20 个关键字 该文档将包含所有英文字符 单词 我感兴趣的是 年龄 23 之类的东西 这里 Age 是我感兴趣的关键字 也想提取 23 它的值 我想到的第一个方法是将整个页面提取为文本
  • Tesseract OCR 无法检测数字

    我正在尝试用 python 中的 tesseract 检测一些数字 下面您将看到我的起始图像以及我可以将其简化为的内容 这是我用来获取它的代码 import pytesseract import cv2 import numpy as np
  • Tesseract OCR:解析表格单元格

    我正在使用 cmd 中的 Tesseract OCR v4 0 0 alpha 从如下所示的表格的 png 中提取文本 我希望 Tesseract OCR 能够解析一个单元格中的内容 然后再转到下一个单元格 我不想继续 行 中的下一个单词
  • 如何使 Tesseract 更快 [关闭]

    Closed 这个问题需要多问focused help closed questions 目前不接受答案 这是一个很遥远的事情 但我必须问 我需要任何可以使 Tesseract OCR 引擎更快的想法 我正在处理由大约 2000 万页文本组
  • 当我使用 pytesser 运行 tesseract 时,如何隐藏控制台窗口

    我是Python新手 我正在从事 OCR 项目 我在 Windows 7 上使用 Python 2 7 12 我已在路径 C Program Files x86 Tesseract OCR 中安装了 tesseract 我在这里找到了 py
  • 将扫描的 PDF 转换为可搜索的 PDF(在 R 中)

    我正在尝试使用以下命令将一系列扫描的 PDF 转换为可搜索的 PDFtesseract and pdftools包 我已经完成了两个步骤 现在我需要写回一个可搜索的pdf 阅读扫描版 PDF Run OCR 写回可搜索的 PDF eg lt
  • 超立方体错误:警告。分辨率 0 dpi 无效。使用 70 代替

    Error was reported when running tesseract on a image image attached tesseract rsa out jpg stdout Warning Invalid resolut
  • 文本二值化

    I d like to binarize this image to use it with tesseract ocr Currently I managed to get this But I need clear image with
  • tesseract 无法识别该图像中的这个单词,这正常吗?

    我需要从这样的小图像中提取单词 我在命令行中使用带有西班牙语选项的 tesseract 如下所示 tesseract category png l spa psm 7 category txt 我认为该文本一定很容易被 OCR 解析 但该单
  • android ndk-构建错误

    我正在尝试为 Android 构建 tesseract 我已将 tesseract 放入示例文件夹中 C Android NDK android ndk r8 samples tesseract之内tesseract我有的文件夹tesser
  • Python Tesseract 无法识别这种字体

    我有这个图像 我想使用 python 将其读取为字符串 我认为这并不难 我发现了 tesseract 然后是使用 tesseract 的 python 脚本的包装器 所以我开始阅读图像 效果很好 直到我尝试阅读这张图像 我是否需要训练它来读
  • 无法在 Mac 上安装 Tesseract-OCR

    我正在尝试使用 pytesseract 在 python 2 7 14 中制作 OCR 程序 当我运行我的代码时 from PIL import Image import pytesseract print pytesseract imag
  • tesseract (v3.03) 输出为 PDF [关闭]

    Closed 这个问题不符合堆栈溢出指南 help closed questions 目前不接受答案 为什么会返回这个错误呢 root amd 3700 2gb ocr test tesseract l dan pdf png out pd
  • Tesseract 是否会忽略扫描文档中的任何非文本区域?

    我正在使用 Tesseract 但我不知道它是否忽略任何非文本区域并仅针对文本 我是否必须删除任何非文本区域作为预处理步骤以获得更好的输出 Tesseract 有一个非常好的算法来检测文本 但它最终会给出误报匹配 理想情况下 您应该在将图像
  • 无法将 Tesseract OCR 模块添加到 Android Studio

    我按照此处找到的分步指南进行操作 https www codeproject com Articles 840623 Android Character Recognition https www codeproject com Artic
  • 使用 Tesseract 进行手写识别

    我只是想知道 如果将大写字母全部放在表格中自己的小框中 那么超正方体的手写识别准确度有多高 我知道你可以训练它来识别你自己的笔迹 但我的问题是我需要在多个笔迹中使用它 有人能指出我正确的方向吗 多谢 简而言之 您必须训练 Tesseract
  • tesseract 处理后无法获取原始彩色位图 - android

    我使用 android 的 tesseract 库从图像中捕获某些文本 我知道捕获的图像不会保存在任何地方 它会被回收 我需要找到原始的彩色位图 我一直在尝试找到原始的彩色位图 但我所能找到的只是灰度位图 Bitmap bitmap act

随机推荐