检测扫描文档中的空页

Detecting empty pages in scanned documents

提问人:sbi 提问时间:3/9/2011 更新时间:10/13/2017 访问量:7793

问:

因此,我们需要检测由扫描仪创建的图像是否代表空白页面。在图像处理方面,我远远超出了我的深度,所以我必须由社区来运行它。

这是我到目前为止想出的:

  • 空白页面可以是明显的白色、灰色再生纸或泛黄的旧纸。目前的想法是为页面创建一个直方图,寻找曲线的急剧增加,并获得比这更暗的像素百分比。如果超过阈值,则页面可能不是空的。

  • 由于这可能会将顶部包含单行文本的页面归类为空,因此我们将平铺该页面并收集有关每个磁贴的统计信息。

  • 我们需要检测扫描的订书机和装订孔(可能只在某些瓷砖中),但这可以推迟到以后的某个阶段。但是,如果您知道除了这两个之外还需要注意什么,请在评论中提及。

  • 这需要快速。它是文档处理工作流程的一部分,每天处理(数万)页。如果处理一个页面需要十秒钟的时间,那么我们的客户将不得不告诉他们的客户,他们必须等待几天才能获得结果。(如果这导致更多的误报,一些客户宁愿让某人检查几十个找到的“空”页面,也不愿让他们的客户再等一天。

所以这是我的问题:

  1. 走这条路是个好主意还是有更好的方法?

  2. 如果我们这样做,我该怎么做?什么是寻找页面阈值的好(廉价)算法?我们能否通过假设一批文档的类似阈值来获得显着的速度?在记录之前,亮度值可以四舍五入到什么精度?我们可以期待什么怪癖?

算法 图像处理

评论

2赞 Fred Foo 3/9/2011
有趣的问题,+1。您是否考虑过训练一些感知器或支持向量机?
4赞 Steve Jessop 3/9/2011
另外,如果页面仅包含文本“此页面故意留空”怎么办?;-)
1赞 sbi 3/9/2011
@Xaade:我们必须与可能每月扫描、压缩、OCR 和存档数十万页的客户合作。当一些扫描操作员在其中一个扫描仪上遗漏了一个明显的苍蝇斑点时,他们不想重新处理 25k 页,因为这就像烧钱一样。然后纸张本身也可能有污渍。想想这个,就像你想想修复你从黑胶唱片中复制的音乐的软件一样:是的,可能在某个地方有一个完美的唱片副本,但你必须使用你得到的东西,所以你使用软件来补偿。
1赞 Dan 3/11/2011
可能要考虑添加“信号处理”标签 - 即使图像处理是一个正确和精确的标签,也许向更广泛的潜伏者群体开放它可能会有所帮助。有趣的问题/问题,顺便说一句。(我觉得无权编辑/更改您的标签......在其他情况下,它更明确。
1赞 maxschlepzig 4/30/2018
DSP.SE 相关问题:快速空页检测

答:

2赞 thecoshman 3/9/2011 #1

如果您知道扫描的页面将完全填充图像,那么计算标准偏差可能是一个很好的方法。

我建议稍微模糊页面以减少一些噪音。然后计算页面的 SD,理论上,或多或少只有一种颜色的页面将具有较低的 SD,而具有大量文本的页面将具有更高的 SD。然后是“训练”系统,以计算出页面何时是纯文本,何时是文本。您可能会发现某些页面很难分辨。

你可以通过让它处理大量的页面来训练它,它遍历了所有页面,你说它是否是普通的。

编辑

好的,带有黑色文本的白色页面,如果我们只有页面而没有周围的东西,则平均颜色为灰色,可能是相当浅的灰色。获取平均值是遍历所有像素的 for 循环,将它们的值相加,然后除以像素数。我不擅长这个 o(logN) 的东西,但可以说,它不会那么久。除非你有巨大的图像。

SD 是秒 for 循环,这次我们计算每个像素与平均值的差异,然后除以平均值。这将花费比平均值更长的时间,因为我们必须做类似的事情

diff = thispixel - mean;
if(diff < 0) {
    diff = -diff;
}
runningTotal += diff;

对于纯色页面,每个像素将接近平均值,因此我们的标清会很低。如果 SD 低于某个值,我们可以假设这意味着页面都是一种颜色。

如果文本量非常少,这可能会有问题,因为它不会对 SD 产生太大影响,所以也许就像您在问题中建议的那样,将页面分成几个部分。我建议水平条带,因为文本往往会这样。如果我们一次做一个这些条带,一旦一个条带表明它有文本,我们就可以停止,因为我们不在乎其余的是否为空白。

模糊页面将有助于减少噪点,因为噪点的奇数像素会减少其影响,从而为您提供“更紧密”的标清。您也可以使用它来降低图像的分辨率。

假设您的酱汁图像是 300 宽 x 900 高,您可以以 9、3 *3 为一组的块对像素进行采样,从而最终得到 100 宽 x 300 高的图像,因此它实际上可以用来减少您需要执行的计算量,在本例中减少九分之一!

主要问题在于仅用一个普通的页面计算出 SD 可以有多高。也许让它找到一堆空白页的 SD。

听上去,你可能想要一个中间立场,让它不确定并要求人为干预,可能让人类价值训练系统变得更好?

评论

0赞 sbi 3/9/2011
我不确定模糊是否不需要太多的性能。如果模糊是微不足道的,请纠正我,但我们在这里谈论的是数万页(有些客户可能有数百万页)。
0赞 sbi 3/9/2011
另外,我有点怀疑 SD 是否是做到这一点的好方法。扫描的文档通常是在大部分白色背景上的一些相当黑色的像素。该曲线可能与经典的SD钟形曲线正好相反。(但是,正如我所说,我对此已经超出了我的深度,所以如果我错了,请不要犹豫,纠正我。
0赞 thecoshman 3/9/2011
好吧,我的逻辑是,一个大部分普通的页面将具有低 SD,因为它们大多是相同的颜色。高标清意味着无论平均值是多少,都存在很大的差异,这只能是因为页面不是平均颜色。平滑可能不需要,但它将有助于减少噪音,因此可以提供更好的结果。你只需要尝试一下,看看
0赞 Steve Jessop 3/9/2011
@sbi:我的显卡可以在 1920x1200 分辨率下“模糊”(即全屏抗锯齿)50-100fps而不会出汗,所以原则上至少这不是一个主要成本。不过,显然这是一个特殊用途的套件。
0赞 Steve Jessop 3/9/2011
@sbi:SD = 标准差,而不是标准正态分布。任何分布都有一个标准差,无论它是否是钟形曲线。
0赞 Lee Louviere 3/9/2011 #2

看起来您正在尝试将公司的所有文书工作转换为数字文档。其中一些论文可能真的很旧。

假设您的文本是黑色的,任何其他颜色都是背景。如果你取两个加权平均值,一个由你认为是文本的内容组成,一个由背景组成,你可以比较这两者,看看它们是否足够遥远,可以考虑进一步的评估。这将消除纸张的任何不均匀老化。

纸张上的订书钉孔和打孔的尺寸非常标准,但如果在白色背景上扫描,它们会显示为灰色或根本不显示。如果没有,那么您可以猜测它们在哪里并删除它们。

现在,我们看一下高度感兴趣的区域,即黑色像素最密集的区域。选择其中的一部分并对其进行 OCR。将起始位置放在左上角最靠近文本开始的区域。在典型的文档中,一个从左到右的实心空白线性区域和另一个从上到下的空白线性区域表示段落的顶部和左侧。您可以确定您有一行文本,因为一行文本下方是另一个从左到右的空白区域。因此,您无需担心选择会将文本切成两半的部分。

评论

0赞 sbi 3/10/2011
实际上,除了一些测试数据外,我们没有转换任何 ouselves。我们只是在为这样做的公司编写软件。 正如我已经回复 Steve 的那样,OCR 不是一种选择,因为避免必须对空白页面进行 OCR 是删除空白页面的一大动力。OCR 成本高昂,因为它占用了性能,会发出误报,并且可能会获得每页版税的许可。此外,OCR 不会找到只有图片的页面(尽管 OCR 有时会尝试在图片中找到的内容很神奇......),我们不能删除这些页面。因此,使用 OCR 执行此操作不是一种选择。:)
2赞 sclv 3/10/2011 #3

执行某种简单的边缘检测。如果构成边缘的像素数低于某个阈值,则页面很有可能是空的。这可以通过将某些与冲孔和订书钉高度确定性(按形状和位置)相对应的边缘分类为微不足道,并将其从指标中剔除来改善。

评论

0赞 sbi 3/10/2011
不过,这不会错过照片吗?
0赞 sclv 3/10/2011
@sbi -- 照片有棱角!而且,照片和页面中非照片的部分之间肯定存在着不小的优势。
0赞 sbi 3/10/2011
因此,让我们来研究一下这个想法。什么是快速边缘检测算法来检测文本和照片中的边缘?为了进行比较:直方图的想法是 O(n)(其中 n 是像素数),每个像素的简单舍入。边缘检测能接近这个水平吗?
0赞 sclv 3/10/2011
有数以百万计的边缘检测算法,其中许多适用于嵌入式硬件上的实时分析。复杂性绝不会杀死你。无论如何,你只需要一个相当便宜、肮脏的版本。这是我在快速谷歌上找到的一个 O(n):math.wustl.edu/~victor/papers/mpedge.pdf
0赞 sbi 3/11/2011
你看过那张纸上的图 5(第 7 页)吗?该算法的结果看起来很像该算法在扫描仪的玻璃不是很干净的情况下可能得出的结果。我仍然持怀疑态度。
0赞 Benjamin 3/10/2011 #4

您可以取扫描图像每几行的平均灰度级别(整数)(取决于分辨率和捕获一行文本所需的行数),然后考虑行均值的分布。如果页面上没有文字,则均值的分布应该很小(即背景范围为 250-255),如果整个页面或部分页面上有文本,则分布会大得多(即文本为 15 到 250 为背景)。

在我看来,由于要检查的页面数量众多,解决方案在计算上应该是简单的。需要进一步处理的方法(边缘检测、过滤等)似乎有点矫枉过正,并且需要更长的时间才能运行。

无需逐个像素地处理,使用矩阵将有助于提高效率,例如使用 Numpy,您可以更有效地一次计算整行、列或矩阵的平均值、总和等。也不需要处理每个像素,一个好的行样本应该能够以类似的精度完成任务。8 位精度应该没问题,您甚至可以在运行此处理算法之前重新采样到大像素。

评论

0赞 sbi 3/11/2011
嗯,重新采样难道不是那些“进一步处理”阶段之一,会扼杀性能吗?无论如何,这似乎是一个尝试的好主意。我会多想一想,然后把它扔进帽子里。谢谢!
0赞 Benjamin 3/11/2011
@sbi,是的,会的。我的意思是建议每 2 个像素掉落一次,以获得宽度和高度一半的图像,这可以轻松快速地完成,并且可以缩短处理时间。
2赞 Fred Nurk 3/12/2011 #5

当我在一家文档处理商工作时(~8 年前),我们处理的客户项目从非常“干净”的只有美国信纸大小的页面到与普通页面混合的不规则形状的封面/卡片纸。操作员将预先分类的文件送入扫描机,只需注意折叠的边角和类似的机械问题。它们的输出是数百个图像的多个流,对应于一系列文件。一名扫描仪操作员可以在一个班次内轻松扫描 15k 张纸(仅为 0.60 页/秒,而高速扫描仪可以处理 3 页/秒,并且仍可扫描两面)。后来的操作员处理了那些寻找关键页面以标记文件开始和结束的页面。(有时可以在这里使用图像识别,但人们也会对第一个操作员进行质量检查。我们有许多变量可以为每个客户项目设置。

我根据这种经历以及您的目标和工作流程的相似之处,在下面大致列出大纲。

(术语:我所说的客户是指我们的客户,例如特定的银行。项目或客户项目是来自该客户的一组文件,其中包含许多文件,例如特定分支机构在给定年份处理的所有抵押贷款。文件是一种逻辑排列,通常是客户之一的物理文件夹,例如一个地址的所有抵押贷款文件。

  1. 切掉顶部、底部、侧面和角落。将它们从计算中剔除(即使您可能会将它们存储在最终图像中)。这将覆盖订书钉孔、活页夹孔,以及(微小的)折叠角和显示为黑点的非常微小的撕裂边缘。根据扫描方式的不同,后两个问题可能不大。

    根据需要,为每个客户项目改变这些切割的尺寸。例如,即使是非常薄的边缘切片,比如 1-2 毫米,也可以消除大多数不规则的边缘,而不会增加误报率。

  2. 转换为黑白,每像素 1 位。无论如何,我怀疑你已经在为一些客户项目做这件事了,所以高效和有效地做这件事,这可能是微妙的,应该不需要额外的工作。(即使您不将 1bpp 图像存储为可交付结果,转换也将有助于空页检测。通过删除任何没有或只有一个黑色邻居的黑色像素(使用所有周围的 8 个作为邻居)来消除噪点。

    在剪切四肢 (#1) 和这种简单的降噪之后,空白页的黑色像素数量将非常少;大多数空白将完全没有黑色像素 - 排除了特别差的页面质量、墨迹印章(扫描背面时,下面会详细介绍)或整个项目中的其他情况,等等。

  3. 根据客户项目的不同,您可以设置要监视的热点 - 与切断侧面相反。例如,观看页面顶部出现单行的 1 英寸条带可能会减少误报。只有一行文字的低对比度扫描件或褪色的硬拷贝(甚至可能是铅笔,这在背面很常见)将以这种方式与空白页区分开来。

    哪些部分值得关注取决于每个项目,但不要尝试将页面划分为多个磁贴,然后将这些磁贴细分为感兴趣的区域。相反,在页面级别并行化它;例如,每个核心 1 个工作线程,每个工作线程一次处理一整页。

  4. 根据你对单个文件进行抠像的方式,你可能会发现删除空白(在标记文件开头页面之前,即使在高音量下,这通常仍然是一个手动过程)然后在文件被抠像后在意想不到的位置观察空白页很有帮助(例如,预期是文件的最后一页,而不是连续两个空白, 等)。

    例如,如果一个特定的项目只扫描每页的一侧,那么连续检测到两个空白页就是一个很好的迹象,表明文件中的几页被颠倒了(客户经常交出这样的硬拷贝文件)。无论是分拣员(去除订书钉和回形针之类的东西)还是第一批机器操作员都应该发现这个错误,但无论如何,它现在需要手动检查来验证。

    另一方面,有些项目的文件非常干净,因此排序器可以插入(通常是彩色的)空白页来标记文件边界。在这种情况下,第二组人员仍然按文件编号进行键入,但只需要检查每个文件的第一页。这种情况并不罕见,但也不常见。

在我开始喋喋不休之前,我希望我的主要观点是:你必须决定如何降低误报率(=数据丢失)和漏报率(=烦人的空白,否则是无害的,但允许的最大率仍然可以在项目合同中指定)。这因项目和您正在处理的文件/文档类型而异,但它会指导您如何进行检测。与尝试一刀切的方法相比,您将从量身定制的方法中获得更好的结果,即使量身定制的方法有 80-98% 的相似度。

例如,如果您要向客户端交付 1bpp 图像,您甚至可能不希望/需要消除空白,因为文件大小(以及最终交付数据集的大小)不会成为问题。当消除大多数空白更难同时保持低误报率时,这可能是一个可以接受的权衡;例如,对于带有墨迹印章的文件(例如,“收到日期”、“接受”、“截止日期”等;它们会渗到背面)或其他问题。

2赞 Norman Ramsey 3/14/2011 #6

我的秋季课程做了一堆图像处理项目。 这是我会尝试的:

  1. 从彩色到灰度的项目
  2. 将所有像素倒入一个简单的直方图中,例如 100 个介于 0 和 1 之间的桶
  3. 在直方图中找到一个局部最小值,使 的绝对值尽可能小,其中是较亮像素的数量,是较暗像素的数量above - belowabovebelow
  4. 强制像素变为白色,将像素变为黑色abovebelow
  5. 如果您愿意,作为额外的步骤,您可以删除黑边
  6. 如果几乎没有任何黑色像素,则页面为空白

前两个步骤应该结合起来,它们是唯一耗时的步骤;在 600dpi 的图像上,您可能需要触摸数百万像素。其余的将是闪电般的速度。如果你不能每秒对多张图像进行分类,我会感到非常惊讶——特别是如果你知道不会有黑边。

唯一需要训练或实验的部分是最后一步。您也可能需要摆弄直方图中的桶数;如果存储桶过多,则可能具有错误的本地最小值。

祝你好运,并向我们报告你是如何做到的!

1赞 HairOfTheDog 11/2/2012 #7

看看这个线路检测算法:http://homepages.inf.ed.ac.uk/rbf/HIPR2/linedet.htm。除了对算法工作原理的详细说明外,还有一个演示,您可以在其中使用自己的图像并查看结果。我尝试了两张图片:1)收据的黑白扫描件,2)黑白收据的“空白”背面。我尝试过的所有边缘检测算法都在“空白”页面上找到了边缘。但是,这种行检测算法是唯一一种在首页上正确找到行但在“空白”后页上找不到任何东西的算法。

评论

0赞 sbi 11/2/2012
谢谢你的分享,但我什至不再在那家公司工作了。不过,这里有一个赞成票给你。:)
0赞 HairOfTheDog 11/2/2012
@sbi 不客气。我正在尝试解决同样的问题。你有没有找到一个简单的解决方案?
0赞 maxschlepzig 10/13/2017 #8

您可以进行嘈杂的修剪,即模糊图像并进行自动修剪(无需实际修改图像)。如果修剪结果的宽度或高度低于阈值(例如,600 dpi 图像的宽度或高度为 80 到 100),则页面为空。

使用 ImageMagick 命令行前端的概念验证:

$ convert scan.png -shave 300x0 -virtual-pixel White -blur 0x15 -fuzz 15% \
    -trim info:

上述命令假定 600 dpi DIN A4 黑白(1 位)图像。它还忽略了 300 像素的边距,因此穿孔等伪影不会产生假阴性