Se os arquivos que você está classificando podem ser modificados ou atualizados ao mesmo tempo, a classificação está sendo executada:
Java 8+
private static List<Path> listFilesOldestFirst(final String directoryPath) throws IOException {
try (final Stream<Path> fileStream = Files.list(Paths.get(directoryPath))) {
return fileStream
.map(Path::toFile)
.collect(Collectors.toMap(Function.identity(), File::lastModified))
.entrySet()
.stream()
.sorted(Map.Entry.comparingByValue())
// .sorted(Collections.reverseOrder(Map.Entry.comparingByValue())) // replace the previous line with this line if you would prefer files listed newest first
.map(Map.Entry::getKey)
.map(File::toPath) // remove this line if you would rather work with a List<File> instead of List<Path>
.collect(Collectors.toList());
}
}
Java 7
private static List<File> listFilesOldestFirst(final String directoryPath) throws IOException {
final List<File> files = Arrays.asList(new File(directoryPath).listFiles());
final Map<File, Long> constantLastModifiedTimes = new HashMap<File,Long>();
for (final File f : files) {
constantLastModifiedTimes.put(f, f.lastModified());
}
Collections.sort(files, new Comparator<File>() {
@Override
public int compare(final File f1, final File f2) {
return constantLastModifiedTimes.get(f1).compareTo(constantLastModifiedTimes.get(f2));
}
});
return files;
}
Ambas as soluções criam uma estrutura de dados de mapa temporária para economizar um tempo constante da última modificação para cada arquivo no diretório. O motivo pelo qual precisamos fazer isso é que, se seus arquivos estiverem sendo atualizados ou modificados enquanto sua classificação está sendo executada, seu comparador estará violando o requisito de transitividade do contrato geral da interface do comparador, pois os últimos tempos de modificação podem estar mudando durante a comparação.
Se, por outro lado, você sabe que os arquivos não serão atualizados ou modificados durante a sua classificação, poderá obter praticamente qualquer outra resposta enviada a esta pergunta, da qual sou parcial:
Java 8+ (nenhuma modificação simultânea durante a classificação)
private static List<Path> listFilesOldestFirst(final String directoryPath) throws IOException {
try (final Stream<Path> fileStream = Files.list(Paths.get(directoryPath))) {
return fileStream
.map(Path::toFile)
.sorted(Comparator.comparing(File::lastModified))
.map(File::toPath) // remove this line if you would rather work with a List<File> instead of List<Path>
.collect(Collectors.toList());
}
}
Nota: Eu sei que você pode evitar a conversão de e para objetos File no exemplo acima, usando a API Files :: getLastModifiedTime na operação de fluxo classificado; no entanto, você precisa lidar com exceções de IO verificadas dentro do lambda, o que é sempre um problema. . Eu diria que se o desempenho é crítico o suficiente para que a tradução seja inaceitável, eu lidaria com a IOException verificada no lambda propagando-a como uma UncheckedIOException ou renunciaria à API do Files por completo e lidaria apenas com os objetos File:
final List<File> sorted = Arrays.asList(new File(directoryPathString).listFiles());
sorted.sort(Comparator.comparing(File::lastModified));