Перейти к основному содержимому

Проверьте, пуст ли каталог в Java

· 2 мин. чтения

1. Обзор

В этом кратком руководстве мы познакомимся с несколькими способами узнать, является ли каталог пустым или нет.

2. Использование Files.newDirectoryStream

Начиная с Java 7, метод Files.newDirectoryStream возвращает DirectoryStream <Path> для перебора всех записей в каталоге . Таким образом, мы можем использовать этот API, чтобы проверить, является ли данный каталог пустым или нет:

public boolean isEmpty(Path path) throws IOException {
if (Files.isDirectory(path)) {
try (DirectoryStream<Path> directory = Files.newDirectoryStream(path)) {
return !directory.iterator().hasNext();
}
}

return false;
}

Для входных данных, не относящихся к каталогу, мы вернем false , даже не пытаясь загрузить записи каталога:

Path aFile = Paths.get(getClass().getResource("/notDir.txt").toURI());
assertThat(isEmpty(aFile)).isFalse();

С другой стороны, если ввод является каталогом, мы попытаемся открыть DirectoryStream для этого каталога. Тогда мы будем считать каталог пустым тогда и только тогда, когда первый вызов метода hasNext() возвращает false . В противном случае он не пуст:

Path currentDir = new File("").toPath().toAbsolutePath();
assertThat(isEmpty(currentDir)).isFalse();

DirectoryStream — это Closeable ресурс, поэтому мы заключаем его в блок try -with-resources . Как и следовало ожидать, метод isEmpty возвращает true для пустых каталогов:

Path path = Files.createTempDirectory("foreach-empty");
assertThat(isEmpty(path)).isTrue();

Здесь мы используем Files.createTempDirectory для создания пустого и временного каталога.

3. Использование Files.list

Начиная с JDK 8, метод Files.list использует для внутреннего использования Files.newDirectoryStream API для предоставления Stream<Path> . Каждый путь является записью внутри данного родительского каталога. Поэтому мы также можем использовать этот API для той же цели:

public boolean isEmpty(Path path) throws IOException {
if (Files.isDirectory(path)) {
try (Stream<Path> entries = Files.list(path)) {
return !entries.findFirst().isPresent();
}
}

return false;
}

Опять же, мы касаемся только первой записи, используя метод findFirst . Если возвращаемый необязательный параметр пуст, то и каталог пуст.

Stream поддерживается ресурсом ввода-вывода , поэтому мы обязательно выпускаем его надлежащим образом, используя блок try-with-resources.

4. Неэффективные решения

И Files.list , и Files.newDirectoryStream будут лениво перебирать записи каталога. Поэтому они будут очень эффективно работать с огромными каталогами . Однако такие решения не будут работать в этом сценарии:

public boolean isEmpty(Path path) {
return path.toFile().listFiles().length == 0;
}

Это с готовностью загрузит все записи внутри каталога, что будет довольно неэффективно при работе с огромными каталогами.

5. Вывод

В этом коротком руководстве мы познакомились с несколькими эффективными способами проверки того, пуст каталог или нет.

Как обычно, все примеры доступны на GitHub .