获取目录中的文件内容

时间:2014-08-01 08:44:00

标签: java file-io java-8

我想获取目录中文件的内容:

/sys/block/sda/device/model

我使用此代码获取内容:

String content = new String(Files.readAllBytes(Paths.get("/sys/block/sda/device/model")));

但在某些情况下,我有这样的情况:

/sys/block/sda/device/model
/sys/block/sdb/device/model
/sys/block/sdc/device/model

如何迭代以

开头的所有目录

sd*并打印文件model

你能告诉我一些带过滤器的Java 8的例子吗?

2 个答案:

答案 0 :(得分:2)

以下是使用Java 8功能执行此操作的示例:

Function<Path,byte[]> uncheckedRead = p -> {
  try { return Files.readAllBytes(p); }
  catch(IOException ex) { throw new UncheckedIOException(ex); }
};
try(Stream<Path> s=Files.find(Paths.get("/sys/block"), 1,
    (p,a)->p.getName(p.getNameCount()-1).toString().startsWith("sd"))) {
  s.map(p->p.resolve("device/model")).map(uncheckedRead).map(String::new)
   .forEach(System.out::println);
}

这是一个努力实现紧凑和独立工作的例子。对于实际应用程序,您可能会以不同的方式执行此操作。将IO操作用作Function并且不允许检查异常的任务非常常见,因此您可能有一个包装函数,如:

interface IOFunction<T,R> {
    R apply(T in) throws IOException;
}
static <T,R> Function<T,R> wrap(IOFunction<T,R> f) {
    return t-> { try { return f.apply(t); }
      catch(IOException ex) { throw new UncheckedIOException(ex); }
    };
}

然后你可以使用

try(Stream<Path> s=Files.find(Paths.get("/sys/block"), 1,
    (p,a)->p.getName(p.getNameCount()-1).toString().startsWith("sd"))) {
  s.map(p->p.resolve("device/model")).map(wrap(Files::readAllBytes))
   .map(String::new).forEach(System.out::println);
}

但是,即使返回的newDirectoryStream不是DirectoryStream,也可能使用Stream,因此需要手动Stream创建,因为此方法允许传递glob模式如"sd*"

try(DirectoryStream<Path> ds
                     =Files.newDirectoryStream(Paths.get("/sys/block"), "sd*")) {
  StreamSupport.stream(ds.spliterator(), false)
    .map(p->p.resolve("device/model")).map(wrap(Files::readAllBytes))
    .map(String::new).forEach(System.out::println);
}

最后,应该提到以文件流的形式处理文件的选项:

try(DirectoryStream<Path> ds
                     =Files.newDirectoryStream(Paths.get("/sys/block"), "sd*")) {
  StreamSupport.stream(ds.spliterator(), false)
    .map(p->p.resolve("device/model")).flatMap(wrap(Files::lines))
    .forEach(System.out::println);
}

答案 1 :(得分:1)

而是使用st*,如果您可以使用以下代码首先搜索路径/sys/block内的现有文件夹,那么效果会更好。

请找到工作示例: -

String dirNames[] = new File("E://block").list();
for(String name : dirNames)
{
    if (new File("E://block//" + name).isDirectory())
    {
        if(name.contains("sd")){
            String content = new String(Files.readAllBytes(Paths.get("E://block//"+name+"//device//model")));
            System.out.println(content);
        }

    }
}