我有一堆我想要阅读的文件,但每个文件都经过加密和压缩。我想通过使用每个核心打开文件,解密并解压缩来加快进程。然后传递给下一个未使用的文件。
现在我有一个for循环,一次读取一个文件解密,解压缩并传递给下一个文件。
怎么做?
答案 0 :(得分:1)
我认为文件IO可能比处理更容易成为瓶颈。无论哪种方式,并行读取文件只会导致硬盘抖动 - 可能是SSD或高端RAID会应付。
我会这样构建程序:
Thread
读取文件并将其转储到BlockingQueue
ThreadPool
和take()
让我们假设您有一些方法void doMagicStuff(byte[] file)
可以对文件做任何事情。
public static void main(String[] args) throws Exception {
final BlockingQueue<byte[]> processingQueue = new LinkedBlockingQueue<>();
final ExecutorService executorService = Executors.newFixedThreadPool(Runtime.getRuntime().availableProcessors());
final AtomicBoolean done = new AtomicBoolean(false);
IntStream.range(0, Runtime.getRuntime().availableProcessors()).forEach(i -> {
executorService.submit(() -> {
while (!done.get() || !processingQueue.isEmpty()) {
try {
doMagicStuff(processingQueue.take());
} catch (InterruptedException e) {
//exit
return;
}
}
});
});
final Path folder = Paths.get("blah/blah");
try (final Stream<Path> files = Files.list(folder)) {
files.filter(Files::isRegularFile)
.map(file -> {
try {
return Files.readAllBytes(file);
} catch (IOException e) {
throw new RuntimeException(e);
}
}).forEach(processingQueue::add);
}
done.set(true);
executorService.shutdown();
executorService.awaitTermination(Integer.MAX_VALUE, TimeUnit.DAYS);
}
public static void doMagicStuff(final byte[] data) {
//MAGIC MAGIC
}
答案 1 :(得分:0)
我会使用paralelStream()例如
Map<String, String> allFiles =
Files.walk(Paths.get("dir"))
.parallel()
.filter(f -> f.toString().endsWith(".gz"))
.collect(Collectors.toMap(f -> f.toString(), f -> decryptAndUncompress(f)));