gpt4 book ai didi

java - 处理 100 万个文件大小在 kbs 到 100 GB 之间的文本文件

转载 作者:行者123 更新时间:2023-11-30 06:01:31 25 4
gpt4 key购买 nike

我想处理从顶级目录路径开始的大量文件,并对目录中的每个文件应用转换(将 char a 转换为 char b)目录以及任何子目录中的任何文件。如果顶级目录路径是“/path/to/directory”,则输出结果将写入路径“/path/to/directory-converted”处的目录。目录深度和文件数量可以是任意大,1,000级深度和1,000,000个文件。每个输入文件可以任意大,例如大小为 100GB。

我首先编写一个递归函数,该函数从顶级目录开始,并使用 new java.io.File(pathToDirectory) 创建一个新文件,检查文件是否是文件或目录并进行转换。

private void applyTransform(File parentFile) {
for (File fileEntry : parentFile.listFiles()) {
if (fileEntry.isDirectory()) {
applyTransform(fileEntry);
} else {
//transform the file
}
}
}

由于递归方法会导致堆栈溢出,因此我将其更改为使用队列并获取要处理的文件列表。

public List<String> getAllFilesToTransform(String pathToDir) {
List<String> result = new ArrayList<>();
Queue<String> queue = new LinkedList<>();
queue.add(pathToDir);

while (!queue.isEmpty()) {
String currentPath = queue.poll();
File currentFile = new File(currentPath);
for (File file : currentFile.listFiles()) {
if (file.isDirectory()) {
queue.add(currentPath + "/" + file.getName());
} else {
result.add(currentPath + "/" + file.getName());
}
}
}
return result;
}

现在我有了要处理的文件列表,我可以开始处理每个文件了。由于每个文件最大可达 100 GB,因此我开始读取每个文件并对文件中的字符应用转换。

private void processFile(String filePath) {
try {
BufferedReader bufferedReader = Files.newBufferedReader(Paths.get(filePath));
char[] chars = new char[4096];
while (bufferedReader.read(chars) != -1) {
transformChars(chars, filePath);
BufferedWriter writer = new BufferedWriter(new FileWriter(pathToDir));
writer.write(fileText);
writer.close();
}
} catch (IOException e) {

}
}

private void transformChars(char[] chars, String filePath) {
try {
BufferedWriter writer = new BufferedWriter(new FileWriter(pathToDir, true));
//transform char array and append to file
writer.write(fileText);
writer.close();
}

我对多线程以及使用它的潜在影响还不熟悉。我想解决两个问题,但不确定或没有经验,什么是最好的方法和方法。

  1. 我必须处理 1000 万个文件
  2. 每个文件可以为 100 GB。

要处理第一个问题,我是否要在实现 Runnable 接口(interface)的单独类中迭代 getAllFilesToTransform 列表中的每个文件?为了解决第二个问题,我可以在单独的工作线程中读取 x 个字符并对它们运行转换并继续写入目标文件吗?

解决这两个问题的最佳方法是什么?

更新 - 这不是我在工作中尝试实现的实际要求,而是作为我学习处理扩展问题并使用多线程解决它们的模拟。

最佳答案

对于文件数量:假设您采用整体设计(即一个进程):

  1. 实现FileVisitor它将文件插入到阻塞队列中。
  2. 使用walkFileTree()与该文件访问者。
  3. 使用该队列构建 ThreadPoolExecutor .

对于文件的大小 - 如果您不知道哪些文件是 100GB,哪些文件是 1k(即,就您而言,它是随机的),那么只需让一项任务处理一个输入文件和一个输出文件。缓冲流针对大文件进行了优化,系统不会在内存中保留 100GB。

关于java - 处理 100 万个文件大小在 kbs 到 100 GB 之间的文本文件,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/57351007/

25 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com