Reputation: 1709
In Java, How do I list only subdirectories from a directory?
I'd like to use the java.io.File functionality, what is the best method in Java for doing this?
Upvotes: 124
Views: 234372
Reputation: 10102
This will literally list (that is, print) all subdirectories. It basically is a loop kind of where you don’t need to store the items in between to a list. This is what one most likely needs, so I leave it here.
Path directory = Paths.get("D:\\directory\\to\\list");
Files.walk(directory, 1).filter(entry -> !entry.equals(directory))
.filter(Files::isDirectory).forEach(subdirectory ->
{
// do whatever you want with the subdirectories
System.out.println(subdirectory.getFileName());
});
Upvotes: 3
Reputation: 121
File files = new File("src");
// src is folder name...
//This will return the list of the subDirectories
List<File> subDirectories = Arrays.stream(files.listFiles()).filter(File::isDirectory).collect(Collectors.toList());
// this will print all the sub directories
Arrays.stream(files.listFiles()).filter(File::isDirectory).forEach(System.out::println);
Upvotes: 1
Reputation: 1
You can use the JAVA 7 Files api
Path myDirectoryPath = Paths.get("path to my directory");
List<Path> subDirectories = Files.find(
myDirectoryPath ,
Integer.MAX_VALUE,
(filePath, fileAttr) -> fileAttr.isDirectory() && !filePath.equals(myDirectoryPath )
).collect(Collectors.toList());
If you want a specific value you can call map with the value you want before collecting the data.
Upvotes: 0
Reputation: 131326
I'd like to use the java.io.File functionality,
In 2012 (date of the question) yes, not today. java.nio
API has to be favored for such requirements.
Terrible with so many answers, but not the simple way that I would use that is Files.walk().filter().collect()
.
Globally two approaches are possible :
1)Files.walk(Path start, )
has no maxDepth
limitations while
2)Files.walk(Path start, int maxDepth, FileVisitOption... options)
allows to set it.
Without specifying any depth limitation, it would give :
Path directory = Paths.get("/foo/bar");
try {
List<Path> directories =
Files.walk(directory)
.filter(Files::isDirectory)
.collect(Collectors.toList());
} catch (IOException e) {
// process exception
}
And if for legacy reasons, you need to get a List of File
you can just add a map(Path::toFile)
operation before the collect :
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
}
Upvotes: 5
Reputation: 39
ArrayList<File> directories = new ArrayList<File>(
Arrays.asList(
new File("your/path/").listFiles(File::isDirectory)
)
);
Upvotes: 3
Reputation: 3480
The solution that worked for me, is missing from the list of answers. Hence I am posting this solution here:
File[]dirs = new File("/mypath/mydir/").listFiles((FileFilter)FileFilterUtils.directoryFileFilter());
Here I have used org.apache.commons.io.filefilter.FileFilterUtils
from Apache commons-io-2.2.jar. Its documentation is available here: https://commons.apache.org/proper/commons-io/javadocs/api-2.2/org/apache/commons/io/filefilter/FileFilterUtils.html
Upvotes: 0
Reputation: 4884
For those also interested in Java 7 and NIO, there is an alternative solution to @voo's answer above. We can use a try-with-resources that calls Files.find()
and a lambda function that is used to filter the directories.
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) {
...
}
We can even filter directories by name by changing the lambda function:
(path, attributes) -> attributes.isDirectory() && path.toString().contains("test")
or by date:
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
Upvotes: 2
Reputation: 13
Here is solution for my code. I just did a litlle change from first answer. This will list all folders only in desired directory line by line:
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!");
}
Upvotes: 0
Reputation: 2786
A very simple Java 8 solution:
File[] directories = new File("/your/path/").listFiles(File::isDirectory);
It's equivalent to using a FileFilter (works with older Java as well):
File[] directories = new File("/your/path/").listFiles(new FileFilter() {
@Override
public boolean accept(File file) {
return file.isDirectory();
}
});
Upvotes: 136
Reputation: 40149
You can use the File class to list the directories.
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));
Update
Comment from the author on this post wanted a faster way, great discussion here: How to retrieve a list of directories QUICKLY in Java?
Basically:
Upvotes: 167
Reputation: 1333
In case you're interested in a solution using Java 7 and NIO.2, it could go like this:
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();
}
Upvotes: 9
Reputation: 6808
@Mohamed Mansour you were almost there... the "dir" argument from that you were using is actually the curent path, so it will always return true. In order to see if the child is a subdirectory or not you need to test that child.
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));
Upvotes: 14
Reputation: 12545
Given a starting directory as a String
String
path as the parameter. In the method:listFiles
methodUpvotes: 0