6

私が理解しようとしているJavaファイルの行の1つは、次のとおりです。

return new Scanner(file).useDelimiter("\\Z").next();

java.util.regex.Patternのドキュメントに従って、ファイルは「入力の終わりですが、最後のターミネータがある場合はそれまで」を返すことが期待されています。しかし、何が起こるかというと、ファイルから最初の1024文字だけが返されます。これは、正規表現パターンマッチャーによって課せられる制限ですか?これを克服できますか?現在、ファイルリーダーを使用しています。しかし、私はこの振る舞いの理由を知りたいです。

4

4 に答える 4

5

私自身、これを再現することはできませんでした。しかし、私は何が起こっているのかについて光を当てることができると思います。

内部的には、スキャナーは1024文字の文字バッファーを使用します。スキャナーは、可能であれば、デフォルトで読み取り可能な1024文字から読み取り、パターンを適用します。

問題はパターンにあります...それは常に入力の終わりと一致しますが、それは入力ストリーム/データの終わりを意味するものではありません。Javaがパターンをバッファリングされたデータに適用すると、入力の終わりの最初の出現を見つけようとします。1024文字がバッファにあるため、一致するエンジンは位置1024を区切り文字の最初の一致と、それが最初のトークンとして返される前のすべてを呼び出します。

そのため、入力終了アンカーはスキャナーでの使用には有効ではないと思います。結局のところ、それは無限のストリームから読み取っている可能性があります。

于 2010-10-04T17:39:39.827 に答える
2

fileオブジェクトをでラップしてみてくださいFileInputStream

于 2010-10-04T17:43:10.130 に答える
1

Scannerファイルから複数のプリミティブを読み取ることを目的としています。実際には、ファイル全体を読み取ることを意図したものではありません。

サードパーティのライブラリを含めたくない場合は、テキストの場合は/をBufferedReaderラップする、またはバイナリデータの場合はループする方がよいでしょう。FileReaderInputStreamReaderFileInputStream

サードパーティのライブラリを使用しても問題がない場合、Apache commons-ioにはFileUtils、静的メソッドreadFileToStringreadLinesテキスト、およびreadFileToByteArrayバイナリデータを含むクラスがあります。

于 2010-10-04T17:50:26.483 に答える
0

Scannerクラスを使用できます。スキャナーを開くときに文字セットを指定するだけです。つまり、次のようになります。

Scanner sc = new Scanner(file, "ISO-8859-1");

Javaは、ファイルから読み取られたバイトを、指定された文字セットを使用して文字に変換します。これは、何も指定されていない場合(source )のデフォルトの文字セットです(基盤となるOSから)。スキャナーがデフォルトの1024バイトしか読み取らないのに、別のスキャナーではファイルの最後に到達する理由はまだわかりません。とにかく、それはうまくいきます!

于 2013-05-02T12:41:31.007 に答える