java 如何制作 BufferedReader 的副本?
声明:本页面是StackOverFlow热门问题的中英对照翻译,遵循CC BY-SA 4.0协议,如果您需要使用它,必须同样遵循CC BY-SA许可,注明原文地址和作者信息,同时你必须将它归于原作者(不是我):StackOverFlow
原文地址: http://stackoverflow.com/questions/12107049/
Warning: these are provided under cc-by-sa 4.0 license. You are free to use/share it, But you must attribute it to the original authors (not me):
StackOverFlow
How can I make a copy of a BufferedReader?
提问by Sunil
I am using a BufferedReader
constructor to make a new copy of an existing BufferedReader
.
我正在使用BufferedReader
构造函数制作现有BufferedReader
.
BufferedReader buffReader = new BufferedReader(originalBuffReader);
The new buffReader
is working fine, but when I do originalBuffReader.readLine()
it gives me null
. Is there any other way I can make a new bufferReader
without affecting my original BufferedReader
.
新buffReader
的工作正常,但是当我这样做时,originalBuffReader.readLine()
它给了我null
. 有没有其他方法可以在bufferReader
不影响我原来的BufferedReader
.
FYI: I am getting bufferReader as an input to my method; and I do not have a access to the source.
仅供参考:我将 bufferReader 作为我方法的输入;而且我无法访问源代码。
回答by aioobe
Any other way I can make a new bufferReader without affecting my oroginal BufferReader
我可以在不影响我原来的 BufferReader 的情况下制作新的 bufferReader 的任何其他方式
There's no straight forward way of solving it by just creating two BufferedReader
s. (The two readers will consume data from the same source.) You'll have to add another level of buffering on the source, so each reader can read the stream independently.
仅通过创建两个BufferedReader
s没有直接的解决方法。(两个读取器将使用来自同一源的数据。)您必须在源上添加另一个级别的缓冲,以便每个读取器可以独立读取流。
This can be achieved by combining TeeInputStream
from Apache Commons and a PipedInputStream
and PipedOutputStream
as follows:
这可以通过组合来实现TeeInputStream
从Apache的百科全书和一个PipedInputStream
和PipedOutputStream
,如下所示:
import java.io.*;
import org.apache.commons.io.input.TeeInputStream;
class Test {
public static void main(String[] args) throws IOException {
// Create the source input stream.
InputStream is = new FileInputStream("filename.txt");
// Create a piped input stream for one of the readers.
PipedInputStream in = new PipedInputStream();
// Create a tee-splitter for the other reader.
TeeInputStream tee = new TeeInputStream(is, new PipedOutputStream(in));
// Create the two buffered readers.
BufferedReader br1 = new BufferedReader(new InputStreamReader(tee));
BufferedReader br2 = new BufferedReader(new InputStreamReader(in));
// Do some interleaved reads from them.
System.out.println("One line from br1:");
System.out.println(br1.readLine());
System.out.println();
System.out.println("Two lines from br2:");
System.out.println(br2.readLine());
System.out.println(br2.readLine());
System.out.println();
System.out.println("One line from br1:");
System.out.println(br1.readLine());
System.out.println();
}
}
Output:
输出:
One line from br1:
Line1: Lorem ipsum dolor sit amet, <-- reading from start
Two lines from br2:
Line1: Lorem ipsum dolor sit amet, <-- reading from start
Line2: consectetur adipisicing elit,
One line from br1:
Line2: consectetur adipisicing elit, <-- resumes on line 2
回答by bjorncs
Passing in a BufferedReader
instance in the constructor for a new BufferedReader
will not make a copy of the original BufferedReader!
在BufferedReader
构造函数中为 new传递一个实例BufferedReader
不会复制原始 BufferedReader!
What you are doing there is chaining the two reader, in other words, you are buffering the already buffered reader instance. When you call readLine()
on buffReader
, it will call readLine()
on originalBuffReader
.
你在那里做的是链接两个阅读器,换句话说,你正在缓冲已经缓冲的阅读器实例。当你调用readLine()
上buffReader
,它会调用readLine()
上originalBuffReader
。
Take a look here for more details of the chaining of streams: Chaining of Streams
回答by Rami Del Toro
Below is one way to consider creating a new BufferedReader out of the Original BufferedReader.
下面是考虑从原始 BufferedReader 中创建新的 BufferedReader 的一种方法。
Essentially, we are dumping the contents of the original buffered reader into a string and then recreating a new BufferedReader object. To be able to re read the original BufferedReader a second time you can mark it and then after reading it, you can then reset it.
本质上,我们将原始缓冲读取器的内容转储到一个字符串中,然后重新创建一个新的 BufferedReader 对象。为了能够再次读取原始的 BufferedReader,您可以标记它,然后在阅读后,您可以重置它。
One thing to keep in mind is you might want to protect by DDOS attacks, where a very large buffered reader can come in and you might want to avoid reading for ever and filling up the memory, you can basically break the for loop after some point or when a certain condition is met.
要记住的一件事是您可能希望通过 DDOS 攻击来保护,其中一个非常大的缓冲读取器可以进入并且您可能希望避免永远读取并填满内存,您基本上可以在某个时间点后中断 for 循环或者当满足某个条件时。
final String originalBufferedReaderDump;
originalBufferedReaderDump.mark(Integer.MAX_VALUE);
for (String line; (line = originalBufferedReader.readLine()) != null; originalBufferedReaderDump+= line);
originalBufferedReader.reset();
final BufferedReader copiedBufferedReader = new BufferedReader(new InputStreamReader(new ByteArrayInputStream(originalBufferedReaderDump.getBytes())));