我正在编写一个程序来处理多个文件,每个文件的大小约为6 GB(来自服务器的大日志文件)。但是我只使用了25%的CPU(4个CPU线程中有4个可用)因为我无法在不同的线程中拆分程序,所以必须按顺序完成工作。
所以,我考虑同时处理多达4个文件,因为我有一个四核CPU,但我受到硬盘随机磁盘访问性能的限制。
但是过了几天,我将使用带有SSD和8 GB内存的笔记本电脑。是否可以映射内存中每个文件的前1 GB并在4个不同的线程中处理它们?当我到达映射文件的末尾时,我应该能够将下一个1 GB的文件映射到内存中以继续。 我认为将1 GB映射到内存应该不是问题,因为它的读取速度大约为400 MB / s。
我知道这可以使用FileChannel完成,但我不确定只映射部分文件。
谢谢, 希比
答案 0 :(得分:1)
当你的内存映射文件时,文件实际上并没有传输到内存(这与内存映射相反)。
而是给你一个内核专门处理的内存地址;当您访问它时,内核会加载包含文件内容的内存页面。然后在操作系统决定回收一些内存时卸载页面;您可以将映射文件视为扩展交换空间。
所有这些都可以说,只要你有足够的内存地址(也就是说,你有64位操作系统和JVM),你就可以映射大于系统内存的文件。
答案 1 :(得分:0)
您可以使用FileChannel立即将整个文件映射到内存中。但是,如果您按顺序读取数据并且处理非常简单,则在每个线程中使用简单的FileInputStream可能会更简单易用,并为您提供相同的性能。
答案 2 :(得分:0)
您想使用可从FileChannel检索的MemoryMappedByteBuffer。另请参阅:Memory-mapped files in Java和此:http://docs.oracle.com/javase/7/docs/api/java/nio/MappedByteBuffer.html
正如Peter指出的那样,如果你的处理不是cpu密集型的,那么在首先处理文件之前将文件移动到内存中可能无法获得太多收益。你可能一下子就这样做会更好。如您所知,复制到内存将不是免费的。