我需要将一些PDF转换为文本。我尝试了许多软性和在线工具,结果总是中等。
为什么从技术上讲这么难?
答案 0 :(得分:7)
我们不要以为您是在谈论只包装一些位图图像的PDF,因为应该清楚,在这种情况下,您只能在所有限制下诉诸OCR。
让我们假设文本是在当前的PDF中绘制的。
在PDF页面上绘制的内容由该页面的内容流中的指令的序列决定。页面上的“绘制文字”表示,在这些指令中,有一些设置了要使用的指令所使用的字体,一些设置了要使用的指令所使用的文本位置和方向,还有一些实际上是由“字符串参数”。
文本提取的任务是从内容流中提取指令序列,而不是按照字体和位置设置指令的指示绘制,以合理的顺序使用标准编码,通常是所用编程语言/平台的字符类型的编码。
第一个问题是了解那些文本绘制指令的字符串参数的编码:
每种字体可以有自己的编码;要提取文本不能简单地忽略所有内容,而是绘制文本并连接其字符串内容的指令,则必须始终考虑当前字体(某些极其简单的文本提取器会忽略此字体,因此,经常无法返回有意义的内容) ;
有很多预定义的编码,有些提醒您知道一些编码,例如 WinAnsiEncoding ,许多您可能不知道的,例如添加-RKSJ-H ;这些编码每个字形可以使用恒定数量的字节,也可以是混合多字节;因此文本提取器必须支持很多编码;
编码也可能是完全即席且任意的;特别是在嵌入子集字体的情况下,经常会看到需要通过从某个起始值处理字符代码而生成的即席编码;即在页面上使用给定字体的第一个字形被赋予起始值作为代码,下一个不同的字形被赋予起始值加一个,下一个不同的字形被赋予起始值加两个,依此类推; “ Hello World”和起始值48(ASCII值“ 0”)将得出“ 01223453627”;这些字体可能可能包含到Unicode的映射,但并非必需。
下一个问题是弄乱字符串的顺序:
字符串绘制指令可以任意顺序出现,例如,“ Hello”可以先绘制成“ lo”,然后移回“ el”,然后再移回“ H”;要提取文本而不能忽略文本定位指令而只需连接文本字符串,就必须始终考虑当前位置(某些简单的文本提取器会忽略此位置,因此可能无法返回有意义的内容);
< / li>多列文字可能会遇到困难,可能会逐行绘制文字,例如首先是第一列顶行的文本,然后是第二列的顶行,然后是第一列的第二行,然后是第二列的第二行,依此类推; PDF中无需暗示文本是多列的。
另一个问题是识别格式或样式工件:
空格不必通过绘制空格标志来创建,也可以通过文本位置更改指令来完成;文本提取器不尝试识别由文本定位指令创建的间隙可能会返回没有空格的结果;另一方面,可以使用相同的技术以最佳距离绘制相邻字形,即字距紧缩;试图识别由文本定位指令创建的间隙的文本提取器可能会错误地返回不应有空格的空格;
有时会打印一些选定的单词,以特别强调;在提取的文本中,这些间隙可能会显示为空格字符,文本的自动后处理可能会将其视为单词分隔符;
通常对于粗体文本使用不同的粗体字体程序;如果还不行,人们有时会创造性地表现出来,并以相同的间隔两次印刷相同的文本来模仿粗体。通过稍大的偏移量(或不同的变换)和不同的颜色,可以模拟阴影效果;如果文本提取器无法识别出该错误,则最终在输出中会有一些重复的字符。
由于不完整或错误的附加信息,还会出现更多问题:
ToUnicode 字体映射(从字符代码到Unicode的可选映射)可能不完整或包含错误;在那里这里有很多关于堆栈溢出的问题,这些问题涉及印度文字的错误 ToUnicode 映射;文本提取结果反映了这些错误;
甚至还有PDF带有矛盾的信息,例如 ToUnicode 映射中有错误,但 ActualText 条目中有正确的信息;一些PDF创建者使用它来允许从某些程序正确复制和粘贴(在这种情况下,建议使用 ActualText 条目),同时在其他程序的输出中注入错误(建议使用 ToUnicode )信息)。
如果您希望文本提取器仅提取页面中最终可见的文本,则会出现另一个问题:
文本可以绘制在当前剪贴区域之外或可见页面区域之外;文本提取器需要牢记这些;
文本可以使用渲染模式“ invisible”绘制;文本提取器必须关注呈现模式;
文本;要认识到这一点,文本提取器不仅可以查看当前指令和一些图形状态详细信息,还必须考虑到在文本位置预先绘制的任何内容;
文本可以绘制为剪切路径;为了识别此文本最后是否可见,只要剪切路径处于活动状态,文本提取器就必须跟踪在文本区域中绘制的内容;
文本稍后可能会被其他内容覆盖;在这种情况下,文本提取器必须删除已识别的文本;但是根据混合模式和透明度设置的不同,这些覆盖物可能会或可能不会使文字发光;因此,为了获得正确的结果,文本提取器必须针对每个字形跟踪其绘制的颜色,背景色以及以后所有这些漂亮效果对这些颜色的影响;当然,字形颜色和背景色都可能很有趣,例如一些阴影颜色;并且所涉及的色彩空间可能不同,因此需要在色彩空间之间来回转换;等等。
此外,在文本提取器通常看起来不像的地方可能会绘制文本:
...
您当然已经了解了为什么文本提取结果不能达到最佳效果的想法。可以肯定的是,以上列表并不完整,文本提取还有更多的麻烦。