目前我正在设计我的产品架构师并面临以下问题。
我有一个Queue,我在其中放置包含字符串和文件名的对象,其中应该写入字符串。
假设我有10个文件说OneFile.txt,twoFile.txt等。 现在我有三个OneFile.txt对象,队列中有五个对象ofFile.txt。
我有多个写入文件的线程。 现在,如果我同步文件编写器对象,那么它将阻止我的其他线程不写入同一文件。
假设有两个线程T1和T2。 T1 Thread正在写入OneFile.txt。 当T1写入OneFile.txt时,T2线程想要写入2File.txt然后T2线程块。 T2不应该是块,因为它想要写两个文件.txt。
请建议什么是好的建筑。 请提供示例代码。
答案 0 :(得分:1)
并行编写是否是一个好主意并不明显。例如。在硬盘上,你通常会慢一点,在SSD上它可以更快,但这取决于你的情况(文件大小,在实际IO之前完成的处理等)。如果你需要它更快,它也不明显。
所以只要使用一个线程,直到你确定它是瓶颈。
答案 1 :(得分:0)
像你这样的接缝可以使用AsynchronousFileChannel(考虑到你运行的是Java 1.7+)。您将为每个需要写入的文件打开一个通道(请参阅open方法)。
这种类型的通道提供了异步写入操作,您可以在其中指定写入应该在文件中的哪个位置 - AsynchronousFileChannel#write(java.nio.ByteBuffer, long, A, java.nio.channels.CompletionHandler)。这使您也可以对同一文本文件进行并行写入。你唯一需要做的就是照顾“下一个写作位置”。您可以通过为每个通道保留一个AtomicLong并使用CompareAndSwap执行并发更新来实现此目的:
以下是来自我们项目的CustomAsyncChannel类的代码的和平:
/**
* Reserves the writing position in this channel with the given size. This method is thread
* safe.
*
* @param writeSize
* Size of writing that has to be done.
* @return Returns the position where file should be written.
*/
public long reserveWritingPosition(long writeSize) {
while (true) {
long writingPosition = nextWritingPosition.get();
if (nextWritingPosition.compareAndSet(writingPosition, writingPosition + writeSize)) {
return writingPosition;
}
}
}
课程本身对你来说应该是一个很好的指南。请注意,写入只能部分完成,您可以在传递给写入操作的CompletionHandler中进行检查。