- PR -

readLineでのEOF検出について

投稿者投稿内容
しろくま
会議室デビュー日: 2003/10/02
投稿数: 11
投稿日時: 2003-11-21 12:00
readLineを用いてテキストファイルの読み込みを行なっているのですが
改行だけのラインのところでnullを返してきてしまいファイルの終了まで
処理が行なえず困っています。
readLineではなく他のメソッドを用いなくてはいけないのでしょうか。
かずくん
ぬし
会議室デビュー日: 2003/01/08
投稿数: 759
お住まい・勤務地: 太陽系第三惑星
投稿日時: 2003-11-21 12:48
BufferedInputStream(or BufferedReader)のreadLineのことですよね。
改行だけだと、空白文字列が返ってきたような気がしたんだけど違ったかな?

問題付近のソースを提示していただけないでしょうか?
ぽん
大ベテラン
会議室デビュー日: 2003/05/13
投稿数: 157
投稿日時: 2003-11-21 12:48
ソースが無いのでいまいち質問内容が理解出来ていないのですが。
以下のソースではどうでしょうか?

コード:

final BufferedReader in = new BufferedReader(new FileReader("foo.in"));
while (in.ready()) {
final String readed = in.readLine();
if (readed == null) {
continue;
}

//何らかの処理
}



[追記]
引用:

かずくんさんの書き込み (2003-11-21 12:48) より:

改行だけだと、空白文字列が返ってきたような気がしたんだけど違ったかな?


Unix上でWindowsの改行コードが使われているファイルを読み込むとnullが帰って来ることがあります。

[さらに追記]
BufferedReaderを用いた場合でした...

[ メッセージ編集済み 編集者: ぽん 編集日時 2003-11-21 13:00 ]
coasm
大ベテラン
会議室デビュー日: 2001/11/26
投稿数: 237
投稿日時: 2003-11-21 12:51
BufferedInputStream#readLine は、
改行だけのラインに対しては空文字列(長さゼロのString)、
EOFに対してはnullを返してきます。

何か勘違いをしているのでは?
しろくま
会議室デビュー日: 2003/10/02
投稿数: 11
投稿日時: 2003-11-21 18:43
linux上で飛んできたメールをシェルでテキストファイルに落とし
そのファイルを以下の処理をかけているのですが
改行だけのラインで終了してしまうのです。
こんな感じです。
try{
fr = new FileReader( file );
br = new BufferedReader( fr );
// 1行単位で入出力
String s;
int i,j,l,m,n;
while((s = br.readLine())!=null){
// 読み込んでの処理
     }


t-wata
大ベテラン
会議室デビュー日: 2002/07/12
投稿数: 209
お住まい・勤務地: 東京
投稿日時: 2003-11-22 12:27
> 改行だけのラインで終了してしまうのです。

while((s = br.readLine())!=null){
// 読み込んでの処理
     }

この読み込んでの処理の部分で、空文字列の処理が例外
になってる可能性はないのですか?
しろくま
会議室デビュー日: 2003/10/02
投稿数: 11
投稿日時: 2003-11-22 13:13
何度も手間を取らせてしまってすみません。
最初から主要部分は記入して置けばいいんですよね。

try{
fr = new FileReader( file );
br = new BufferedReader( fr );
// 1行単位で入出力
String s;
int i,j,l,m,n;
while((s = br.readLine())!=null){
// 読み込んでの処理
System.out.println(s);
}

ですので、何も処理はしていないのが実情です。
下がデータになります。
--------------------------------------------------------
Date: Thu, 20 Nov 2003 09:25:35 +0900
Mime-Version: 1.0
Content-Type: text/plain; charset="iso-2022-jp"
Content-Transfer-Encoding: 7bit

tako
--------------------------------------------------------
これでシステムアウトされたものを見ると
Content-Transfer-Encoding: 7bit
までになってしまうのです。
かずくん
ぬし
会議室デビュー日: 2003/01/08
投稿数: 759
お住まい・勤務地: 太陽系第三惑星
投稿日時: 2003-11-22 15:48
Windows版J2SE1.4.2のBufferReaderのソースコードを眺めると、
EOF判断は、
コード:
	if (nextChar >= nChars)
	    fill();
	if (nextChar >= nChars) { /* EOF */
	    if (s != null && s.length() > 0)
		return s.toString();
	    else
		return null;
	}


となっており、単純化するとこれは、読み込んだサイズが、バッファサイズ以上なら、バッファを更新し、更新後それでも読み込みサイズのほうが大きいなら、EOFであると判断するということです。途中でnullが返るということは、バッファの更新がうまくいっていないのではと思われます。そこでfill()の中身を見ると、いろいろ複雑なことを行っていますが、一番大事な部分は、
コード:
	int n;
	do {
	    n = in.read(cb, dst, cb.length - dst);
	} while (n == 0);
	if (n > 0) {
	    nChars = dst + n;
	    nextChar = dst;
	}


であり、委譲先で読み込めれば、バッファサイズと読み込んだサイズを更新するということです。途中でnullが返るということは読み込めていないのではと思われます。
in.read()をさかのぼると、sun.nio.cs.StreamDecoder#read()まで行き着きますが、私は、sun.nio.cs.StreamDecoderのコードを所有していないのでこれ以上のことはわかりません。
ライブラリのバグの可能性は捨てきれません。

ところで、プラットフォーム、実行VM環境、開発環境は何?

スキルアップ/キャリアアップ(JOB@IT)