0

以下は私のコードのスナップショットです。入力ファイルのサイズは 45 Mb です。

Scanner fileScanner = new Scanner(file);
String scannedFarm;
try{

    Pattern p = Pattern.compile("^(?:.+(?:\\r?\\n|\\Z)){2,}",Pattern.MULTILINE);

    while((scannedFarm = fileScanner.findWithinHorizon(p, 0)) != null){ // Throws Exception
    ...
    ...

例外がスローされる理由を明確にする追加情報を追加します。ファイル形式を説明する関連する質問が役立つ場合があります: Java, Regular Expression HasNext starts with empty line, multiplatform support .

ところで:これはチャームのような小さなファイルで機能しますが、大きなファイルでは失敗します。文字列にはfindWithinHorizo​​nから返される最大サイズがありますか?

アップデート

小さなスタック トレースが要求されたように:

http://pastebin.com/dcJ1jdkf

ファイル スナップショットの小さな例:

http://pastebin.com/EYMsbrKj

4

2 に答える 2

3

Scannerクラスの仕組みはわかりませんが.findwithinHorizon()、正規表現をどうするかは、その正規表現が非常に奇妙です。

この正規表現は、各行が少なくとも1文字の長さである限り、ファイル全体に一度に一致します。空の行がある場合は、少なくとも2行にまたがる空の行の間のすべてのブロックに一致します。それがあなたが実際にやろうとしていることであるなら、それをするもっと良い方法があります:

Pattern p = Pattern.compile("(?:^.+$(?:\\r?\\n)?){2,}", Pattern.MULTILINE);

正規表現エンジンの不要なバックトラックを回避するために、すべての数量詞を所有格にすることができます。

Pattern p = Pattern.compile("(?:^.++$(?:\\r?+\\n)?+){2,}+", Pattern.MULTILINE);

所有格の数量詞の有無にかかわらず、この正規表現は次のように一致します。

スクリーンショットRegexBuddy

于 2012-11-05T21:16:37.020 に答える
0

区切り文字ではなく、トークン自体に一致させる方が簡単だと思います。とメソッドfindWithinHorizon()で表される Scanner の優先操作モードの代替手段です。hasNextXXX()nextXXX()

"(?m)^\\w+;\\w+$(?:\r?\n\\w+(?:;\\w+)+$)+"

データ形式の詳細な説明を提供していないため、サンプルに一致する最も単純な正規表現を使用しました.

于 2012-11-05T22:48:18.117 に答える