2012-08-10 11 views
8

PDF文書を解析する必要があります。私はすでにパーサーを実装してライブラリを使用しましたiTextこれまで問題なく動作しました。PDFを解析する際に奇妙な空白があります

しかし、いいえ、私は単語の真ん中に非常に奇妙な空白を取得する別のドキュメントを解析する必要があります。一例として、私は得る:

VoのRBER eitungアウフMotorrのadsaisonを死にます。 Viele Motorr ADF AHR ER

すべての大胆な言葉が接続されている必要がありますが、何らかの形でPDFパーサが単語に空白を追加しています。しかし、私がコピーしてPDFからTextfileにコンテンツを貼り付けるとき、私はこれらのスペースを取得しません。

まず、私が使用しているPDF解析ライブラリのためだと思っていましたが、別のライブラリでもまったく同じ問題が発生しました。

私は、パースされた単語からsingleSpaceWidthを見ました。そして、それは空白を追加するときに常に変化していることに気付きました。私はそれらを手動でまとめようとしました。しかし、実際には単語を再結合するパターンはないので、ほとんど不可能です。

誰かに同様の問題がありましたか、その問題の解決策がありましたか?

要求されたとして、ここではいくつかのより多くの情報がある:

PdfReader reader = new PdfReader("data/SpecialTests/SuedostSchweiz/" + src); 

SemTextExtractionStrategy semTextExtractionStrategy = new SemTextExtractionStrategy(); 

for (int i = 1; i <= reader.getNumberOfPages(); i++) { 
    // Set the page number on the strategy. Is used in the Parsing strategies. 
    semTextExtractionStrategy.pageNumber = i; 

    // Parse text from page 
    PdfTextExtractor.getTextFromPage(reader, i, semTextExtractionStrategy); 
} 

ここで、実際にtを解析するSemTextExtractionStrategyメソッド内線そこで私は、手動ですべての解析された単語の空白の後に追加し、何とかそれを検出して単語を分割しない:

ここ
@Override 
public void parseText(TextRenderInfo renderInfo, int pageNumber) {  

    this.pageNumber = pageNumber; 

    String text = renderInfo.getText(); 

    currTextBlock.getText().append(text + " "); 

    .... 
} 

は全体SemTextExtractionクラスですが、そこにはそれだけで(parseText)上からメソッドを呼び出しありません。

public class SemTextExtractionStrategy implements TextExtractionStrategy { 

    // Text Extraction Strategies 
    public ColumnDetecter columnDetecter = new ColumnDetecter(); 

    // Image Extraction Strategies 
    public ImageRetriever imageRetriever = new ImageRetriever(); 

    public int pageNumber = -1; 

    public ArrayList<TextParsingStrategy> textParsingStrategies = new ArrayList<TextParsingStrategy>(); 
    public ArrayList<ImageParsingStrategy> imageParsingStrategies = new ArrayList<ImageParsingStrategy>(); 

    public SemTextExtractionStrategy() { 

     // Add all text parsing strategies which are later on applied on the extracted text 
     // textParsingStrategies.add(fontSizeMatcher); 
     textParsingStrategies.add(columnDetecter); 

     // Add all image parsing strategies which are later on applied on the extracted text 
     imageParsingStrategies.add(imageRetriever); 
    } 

    @Override 
    public void beginTextBlock() { 

    } 

    @Override 
    public void renderText(TextRenderInfo renderInfo) { 
     // TEXT PARSING 
     for(TextParsingStrategy strategy : textParsingStrategies) { 
      strategy.parseText(renderInfo, pageNumber); 
     } 
    } 

    @Override 
    public void endTextBlock() { 

    } 

    @Override 
    public void renderImage(ImageRenderInfo renderInfo) { 
     for(ImageParsingStrategy strategy : imageParsingStrategies) { 
      strategy.parseImage(renderInfo); 
     } 
    } 
} 
+0

あなたが使用しているiTextのバージョンを教えてください。何らかの理由でPDFを提供する必要があります。また、解析するコードも必要です。 – Eugene

+0

上記の情報にすべての情報を追加しました。 – Prine

+0

あなたが使っているTextExtractionStrategyクラスはどうですか? – Eugene

答えて

2

私は、次のGhostscriptコマンドで指定したPDFファイルを処理しています。面白い部分は52行目ですが、読みやすくするために複数の行に分けています。

[ 
    (&;&)-287.988 
    (672744)29.9906 
    (+\(%)30.01 
    (+!4)29.9876 
    (&4)-287.989 
    (%4)30.0039 
    (&1&8)-287.975 
    (3=\)!)-288.021 
    (*&4)30.0212 
    (&=23)-287.996 
    (+1%)-287.99 
    (\(=&)-288.011 
    (8&1&)-287.974 
    (672744)29.9906 
    (+\(3+=378$)-250.977 
    (#7\)!) 
]TJ 

括弧内はテキスト文字です。私はそれらのいくつかを変更して、レンダリングされたPDFファイルを見て、どの文字がどのグリフを表すかを見ました。次に、テキストをデコードしました:

[ 
    (ele)-287.988 
    (Motorr)29.9906 *** 
    (adf)30.01 *** 
    (ahr)29.9876 *** 
    (er)-287.989 
    (fr)30.0039 
    (euen)-287.975 
    (sich)-288.021 
    ... 
] 

実際に文字間に空白があります。あなたの場合、これはおそらくフォントのカーニングです。あなたのPDFライブラリがこの空白をどのように解釈するのかという疑問があります。結果として得られる文字列の空白に「負の空白」が描画されているように見えます。

+0

これまたは実装を取り除く方法はありますか? – NinjaOnSafari

+0

とpdfを生成するためにどのツールを使用しましたか? – NinjaOnSafari

+0

それはゴーストスクリプトです。私はそれを明確にする答えを編集しました。ヒントをありがとう。 –

0

あなたが持っている文書が列に分割されているので、明白な誤りが

の内側にあるSemTextExtractionStrategy

クラス。私は、クラスのColumnDetecterがおそらく非難され、iTextではないと仮定します。私はそれが列のサイズに基づいて実装されていると仮定することができ、それに基づいてテキストを取得します。

テキストだけが必要な場合は、列のサイズに基づいて実装が簡単になります。

gs -o out.pdf -q -sDEVICE=pdfwrite -dOptimize=false -dUseFlageCompression=false -dCompressPages=false -dCompressFonts=false whitespacesProblem.pdf 

このコマンドは、ストリームのエンコーディングを持っていないファイルout.pdfを、作成したので、より良い読みやすいです:

+0

あなたの答えをありがとう。間違いなくColumnDetecterを見ていきます。しかし、parseTextメソッドはこのクラスのものであり、そこには単語が既に分割されているiTextライブラリから直接出力が得られます。 – Prine

1

も私のために働いた答えは https://github.com/smalot/pdfparser/issues/72でhuuhungusから見たものですローランドによって、ここに解答で説明しても https://issues.apache.org/jira/browse/TIKA-724

の最初のコメントに見られるように、PDFでの空白は既知の問題です

SR:PDFParserに固有のものであり、それはあなたがこの問題を持っていることがわかっている場合、実際にPDFParserに、この余分なスペースを追加するコードを変更することです

C/Smalot/PdfParser/Object.phpこの行をコメントアウト

$text .= ' '; 

完全にそれを修正するが、彼らはこの問題を助けることができるので、それは許容

他のライブラリも同様の一時的な修正を有することができますありませんある場合には。

+0

iText 5.2.1は現在古代版です。現在のバージョンでは、iTextがどのような状況でスペースを追加するのか、そうでないのかを微調整するためのプロパティ/オーバーライド可能なメソッドが用意されています。スペースを追加しないことも一般的には悪い選択です。多くのPDFはテキストをほとんどスペースなしで抽出します。 – mkl

関連する問題