使用 Java 递归列出目录中的所有文件

新手上路,请多包涵

我有这个函数可以递归地打印目录中所有文件的名称。问题是我的代码非常慢,因为它必须在每次迭代时访问远程网络设备。

我的计划是首先从目录中递归加载所有文件,然后使用正则表达式遍历所有文件以过滤掉所有我不需要的文件。有人有更好的建议吗?

 public static printFnames(String sDir) {
    File[] faFiles = new File(sDir).listFiles();
    for (File file : faFiles) {
        if (file.getName().matches("^(.*?)")) {
            System.out.println(file.getAbsolutePath());
        }
        if (file.isDirectory()) {
            printFnames(file.getAbsolutePath());
        }
    }
}

这只是稍后的测试我不会使用这样的代码,而是将与高级正则表达式匹配的每个文件的路径和修改日期添加到数组中。

原文由 Hultner 发布,翻译遵循 CC BY-SA 4.0 许可协议

阅读 458
2 个回答

假设这是您要编写的实际生产代码,那么我建议使用解决方案来解决已经解决的这类问题 - Apache Commons IO ,特别是 FileUtils.listFiles() 。它处理嵌套目录、过滤器(基于名称、修改时间等)。

例如,对于您的正则表达式:

 Collection files = FileUtils.listFiles(
  dir,
  new RegexFileFilter("^(.*?)"),
  DirectoryFileFilter.DIRECTORY
);

这将递归搜索匹配 ^(.*?) 正则表达式的文件,将结果作为集合返回。

值得注意的是,这不会比滚动您自己的代码快,它在做同样的事情——用 Java 拖网文件系统只是很慢。不同之处在于,Apache Commons 版本没有任何错误。

原文由 skaffman 发布,翻译遵循 CC BY-SA 3.0 许可协议

In Java 8, it’s a 1-liner via Files.find() with an arbitrarily large depth (eg 999 ) and BasicFileAttributes of isRegularFile()

 public static printFnames(String sDir) {
    Files.find(Paths.get(sDir), 999, (p, bfa) -> bfa.isRegularFile()).forEach(System.out::println);
}

要添加更多过滤,请增强 lambda,例如在过去 24 小时内修改的所有 jpg 文件:

 (p, bfa) -> bfa.isRegularFile()
  && p.getFileName().toString().matches(".*\\.jpg")
  && bfa.lastModifiedTime().toMillis() > System.currentMillis() - 86400000

原文由 Bohemian 发布,翻译遵循 CC BY-SA 3.0 许可协议

撰写回答
你尚未登录,登录后可以
  • 和开发者交流问题的细节
  • 关注并接收问题和回答的更新提醒
  • 参与内容的编辑和改进,让解决方法与时俱进
推荐问题