Di Java, Bagaimana cara mencantumkan hanya subdirektori dari direktori?
Saya ingin menggunakan fungsionalitas java.io.File, apa metode terbaik di Java untuk melakukan ini?
Di Java, Bagaimana cara mencantumkan hanya subdirektori dari direktori?
Saya ingin menggunakan fungsionalitas java.io.File, apa metode terbaik di Java untuk melakukan ini?
Jawaban:
Anda dapat menggunakan kelas File untuk mendaftar direktori.
File file = new File("/path/to/directory");
String[] directories = file.list(new FilenameFilter() {
@Override
public boolean accept(File current, String name) {
return new File(current, name).isDirectory();
}
});
System.out.println(Arrays.toString(directories));
Memperbarui
Komentar dari penulis pada posting ini menginginkan cara yang lebih cepat, diskusi hebat di sini: Bagaimana cara mengambil daftar direktori CEPAT di Java?
Pada dasarnya:
Solusi Java 8 yang sangat sederhana:
File[] directories = new File("/your/path/").listFiles(File::isDirectory);
Ini setara dengan menggunakan FileFilter (bekerja dengan Java yang lebih lama juga):
File[] directories = new File("/your/path/").listFiles(new FileFilter() {
@Override
public boolean accept(File file) {
return file.isDirectory();
}
});
::
kerja titik dua ganda dalam hal ini?
@Mohamed Mansour Anda hampir sampai ... argumen "dir" dari yang Anda gunakan sebenarnya adalah jalur saat ini, jadi akan selalu mengembalikan nilai true. Untuk melihat apakah anak itu subdirektori atau tidak, Anda perlu menguji anak itu.
File file = new File("/path/to/directory");
String[] directories = file.list(new FilenameFilter() {
@Override
public boolean accept(File current, String name) {
return new File(current, name).isDirectory();
}
});
System.out.println(Arrays.toString(directories));
Jika Anda tertarik dengan solusi yang menggunakan Java 7 dan NIO.2, itu bisa seperti ini:
private static class DirectoriesFilter implements Filter<Path> {
@Override
public boolean accept(Path entry) throws IOException {
return Files.isDirectory(entry);
}
}
try (DirectoryStream<Path> ds = Files.newDirectoryStream(FileSystems.getDefault().getPath(root), new DirectoriesFilter())) {
for (Path p : ds) {
System.out.println(p.getFileName());
}
} catch (IOException e) {
e.printStackTrace();
}
ArrayList<File> directories = new ArrayList<File>(
Arrays.asList(
new File("your/path/").listFiles(File::isDirectory)
)
);
Bagi yang juga tertarik dengan Java 7 dan NIO, ada solusi alternatif jawaban @ voo di atas . Kita bisa menggunakan try-with-resources yang memanggil Files.find()
dan fungsi lambda yang digunakan untuk memfilter direktori.
import java.io.IOException;
import java.nio.file.Files;
import java.nio.file.Path;
import java.nio.file.Paths;
import java.util.stream.Stream;
final Path directory = Paths.get("/path/to/folder");
try (Stream<Path> paths = Files.find(directory, Integer.MAX_VALUE, (path, attributes) -> attributes.isDirectory())) {
paths.forEach(System.out::println);
} catch (IOException e) {
...
}
Kami bahkan dapat memfilter direktori berdasarkan nama dengan mengubah fungsi lambda:
(path, attributes) -> attributes.isDirectory() && path.toString().contains("test")
atau berdasarkan tanggal:
final long now = System.currentTimeMillis();
final long yesterday = new Date(now - 24 * 60 * 60 * 1000L).getTime();
// modified in the last 24 hours
(path, attributes) -> attributes.isDirectory() && attributes.lastModifiedTime().toMillis() > yesterday
Saya ingin menggunakan fungsionalitas java.io.File,
Pada 2012 (tanggal pertanyaan) ya, bukan hari ini. java.nio
API harus diutamakan untuk persyaratan seperti itu.
Mengerikan dengan begitu banyak jawaban, tetapi bukan cara sederhana yang akan saya gunakan Files.walk().filter().collect()
.
Secara global, dua pendekatan dimungkinkan:
1) Files.walk(Path start, )
tidak memiliki maxDepth
batasan sementara
2) Files.walk(Path start, int maxDepth, FileVisitOption... options)
memungkinkan untuk mengaturnya.
Tanpa menentukan batasan kedalaman apa pun, itu akan memberi:
Path directory = Paths.get("/foo/bar");
try {
List<Path> directories =
Files.walk(directory)
.filter(Files::isDirectory)
.collect(Collectors.toList());
} catch (IOException e) {
// process exception
}
Dan jika karena alasan lama, Anda perlu mendapatkan Daftar File
Anda bisa menambahkan map(Path::toFile)
operasi sebelum pengumpulan:
Path directory = Paths.get("/foo/bar");
try {
List<File> directories =
Files.walk(directory)
.filter(Files::isDirectory)
.map(Path::toFile)
.collect(Collectors.toList());
} catch (IOException e) {
// process exception
}
Files.list(Path)
yang mungkin sama dengan Files.walk(Path,1)
.
Files.list(Path)
adalah alternatif yang adil jika kita tidak ingin mengulang folder secara rekursif. Untuk mengulang folder secara rekursif, walk()
lebih cocok.
Solusi yang berhasil untuk saya, tidak ada di daftar jawaban. Karenanya saya memposting solusi ini di sini:
File[]dirs = new File("/mypath/mydir/").listFiles((FileFilter)FileFilterUtils.directoryFileFilter());
Disini saya telah menggunakan org.apache.commons.io.filefilter.FileFilterUtils
dari Apache commons-io-2.2.jar. Dokumentasinya tersedia di sini: https://commons.apache.org/proper/commons-io/javadocs/api-2.2/org/apache/commons/io/filefilter/FileFilterUtils.html
Diberikan direktori awal sebagai String
String
jalur sebagai parameter. Dalam metode:listFiles
metodeInilah solusi untuk kode saya. Saya baru saja melakukan sedikit perubahan dari jawaban pertama . Ini akan mencantumkan semua folder hanya dalam direktori baris demi baris yang diinginkan:
try {
File file = new File("D:\\admir\\MyBookLibrary");
String[] directories = file.list(new FilenameFilter() {
@Override
public boolean accept(File current, String name) {
return new File(current, name).isDirectory();
}
});
for(int i = 0;i < directories.length;i++) {
if(directories[i] != null) {
System.out.println(Arrays.asList(directories[i]));
}
}
}catch(Exception e) {
System.err.println("Error!");
}