【发布时间】:2020-01-10 09:55:13
【问题描述】:
在我的应用程序中,我正在接收要存储在文件中的数据,并对其进行一些计算。接收和计算都可能持续很长时间,所以我想异步进行。
下面的清单显示了我的基本设置:thread1 生成一些数据并将它们存储在一个文件中。
thread2 读取文件并处理数据。
Thread thread1 = new Thread( () -> {
try {
BufferedOutputStream out = new BufferedOutputStream( new FileOutputStream( "test" ) );
for( int i = 0; i < 10; i++ ) {
//producing data...
out.write( ( "hello " + i + "\n" ).getBytes() );
out.flush();
//Thread.sleep( 10 );
}
out.close();
} catch( Exception e ) {
e.printStackTrace();
}
} );
thread1.start();
Thread thread2 = new Thread( () -> {
try {
BufferedInputStream in = new BufferedInputStream( new FileInputStream( "test" ) );
int b = in.read();
while( b != -1 ) {
//do some calculation with data
System.out.print( (char)b );
b = in.read();
}
in.close();
} catch( Exception e ) {
e.printStackTrace();
}
} );
thread2.start();
根据这个问题,我猜想在同一个文件上同时读写是可以的:FileInputStream and FileOutputStream to the same file: Is a read() guaranteed to see all write()s that "happened before"? 或者我在这里遗漏了什么?
执行上面的清单会产生预期的输出:
hello 0
hello 1
hello 2
hello 3
hello 4
hello 5
hello 6
hello 7
hello 8
hello 9
但是,如果由于某种原因读取器线程比写入器快(可以通过取消注释线程 1 中的 Thread.sleep 行来模拟),则读取器读取 EOF (-1) 并在文件已完全写入。只放了一行:
hello 0
但是作者仍然在“测试”文件中生成整个输出。
现在我想让in.read() 阻塞,直到线程1 中的FileOutputStream 关闭。
我认为这可以通过避免将 EOF 放在文件末尾直到 out 关闭来完成。这是真的吗?如果是,我该怎么做?还是有更好的方法?
【问题讨论】:
-
不,你不能。您应该在编写数据时将数据传递给或通过读取代码。
-
如果你想要一个管道,你应该使用管道......
标签: java concurrency eof fileinputstream fileoutputstream