简体   繁体   English

按日期和大小(文件)对数组进行排序

[英]Sort Array by Date and Size (Files)

I've got a method that returns to me a String[] of names of the Files of a current path, the thing I'm trying to do is make a method that returns to me this String[] of names but sorted by date, and sorted by size, I've almost done this, but I'm missing something.我有一个方法可以返回给我当前路径的Files名称的String[] ,我想做的事情是创建一个方法,返回给我这个String[]的名称但按日期排序,并按大小排序,我几乎已经完成了,但我遗漏了一些东西。 I know to sort it's used Arrays.sort() but the thing is that I don't know how to join all.我知道排序它使用Arrays.sort()但问题是我不知道如何加入所有。

This is what I've got (No sorted)这就是我所拥有的(未排序)

 File dir = new File(this.path);
 File[] filelist = dir.listFiles();
 String[] theNamesOfFiles;
 if (filelist.length == 0) {
     theNamesOfFiles = new String[1];
 } else {
     theNamesOfFiles = new String[filelist.length];
 }

 if (filelist.length == 0) {
     theNamesOfFiles[0] = "This folder is empty";
 } else {
     for (int i = 0; i < theNamesOfFiles.length; i++) {

         theNamesOfFiles[i] = filelist[i].getName();
     }
 }
 return theNamesOfFiles;

Now I tried to do a SortByDate() method but I don't know how to make to get those File[] to make the previous method :现在我尝试做一个SortByDate()方法,但我不知道如何让那些File[]来制作以前的方法:

 public File[] SortByDate(File test) {
 final File[] sortedByDate = test.listFiles();
 if (sortedByDate != null && sortedByDate.length > 1) {
     Arrays.sort(sortedByDate, new Comparator < File > () {
         @Override
         public int compare(File object1, File object2) {
             return (int)((object1.lastModified() > object2.lastModified()) ? object1.lastModified() : object2.lastModified());
         }
     });
     return sortedByDate;
 }
 return sortedByDate;
 }

And I think I know how to get the size of a File doing :而且我想我知道如何获取File的大小:

Integer.parseInt(String.valueOf(filelist[i].length() / 1024))

Shall I do this also with the Compare<File>() ?我也应该用Compare<File>()吗?

What I'm misunderstanding or missing?我误解或遗漏了什么?

EDIT编辑

Now what I've tried is create a private File[] SortedByDate;现在我尝试的是创建一个private File[] SortedByDate; , and I've implemented this method : ,我已经实现了这个方法:

public void SortByDate() {

File test = new File(this.path);
this.SortedByDate = test.listFiles();

if (this.SortedByDate != null && this.SortedByDate.length > 1) {
    Arrays.sort(this.SortedByDate, new Comparator < File > () {
        @Override
        public int compare(File object1, File object2) {
            return (int)((object1.lastModified() > object2.lastModified()) ? object1.lastModified() : object2.lastModified());
        }
    });
}
for (int i = 0; i < this.SortedByDate.length; i++) {
    Log.d("SortedByDate", this.SortedByDate[i].getName());
}
}

And then I've created another method that looks like :然后我创建了另一种方法,看起来像:

public String[] FilesFoundSortedByDate() {
SortByDate();
String[] theNamesOfFiles;
if (this.SortedByDate.length == 0) {
    theNamesOfFiles = new String[1];
} else {
    theNamesOfFiles = new String[this.SortedByDate.length];
}

if (this.SortedByDate.length == 0) {
    theNamesOfFiles[0] = "This folder is empty";
} else {
    for (int i = 0; i < theNamesOfFiles.length; i++) {

        theNamesOfFiles[i] = this.SortedByDate[i].getName();
    }
}
return theNamesOfFiles;
}

And I thought to call the function of SortByDate and then use the File[] of the new attribute created, but it isn't sorting.我想调用SortByDate的函数,然后使用创建的新属性的File[],但它不是排序。

Sorting functions.排序功能。 Modify them as needed.根据需要修改它们。 All they are doing is make use of values and compareTo() method calls.他们所做的只是利用值和compareTo()方法调用。 The key to understanding this is available here .了解这一点的关键可在此处获得

String logic together as needed to form your function for your sort as it is slightly confusing on what the actual sort requirements need to be.根据需要将逻辑串在一起以形成您的排序函数,因为它对实际排序要求需要的内容有些困惑。

 private void sortByName(File[] files){
     Arrays.sort(files, new Comparator<File>() {
        @Override
        public int compare(File t, File t1) {
            return t.getName().compareTo(t1.getName());
        }
    });
}

private void sortByDate(File[] files){
    Arrays.sort(files, new Comparator<File>() {
        @Override
        public int compare(File t, File t1) {
            return (int) (t.lastModified() - t1.lastModified());
        }
    });
}

private void sortBySize(File[] files){
     Arrays.sort(files, new Comparator<File>() {
        @Override
        public int compare(File t, File t1) {
            return (int) (t.length() - t1.length());
        }
    });
}

Sort file list by date ascending and size ascending.按日期升序和大小升序对文件列表进行排序。

 void SortByDateAndSize(File[] fileList) {
    Arrays.sort(fileList, new Comparator<File>() {
        @Override
        public int compare(File o1, File o2) {
            int r = Long.compare(o1.lastModified(), o2.lastModified());
            if (r != 0)
                return r;
            return Long.compare(o1.length(), o2.length());
        }
    });
}

I used the Java 8 Stream and Lamda features, to create a function which sorts the files in a directory by the last modified time and the file size.我使用 Java 8 Stream 和 Lamda 功能创建了一个函数,该函数根据上次修改时间和文件大小对目录中的文件进行排序。

public static String[] getSortedFileNames(File directory) {
    return Arrays
        // get all the files from the directory
        .stream(directory.listFiles())
        // sorting them first by last modified time and then by length
        // the sorted function uses a comparator (like your Comparator<File>
        // or a function which compares two files
        .sorted((f1, f2) -> {
            // first compare the two files by last modified (newest files first => compare f2 with f1)
            final int compareModified = Long.compare(f2.lastModified(), f1.lastModified());
            return compareModified != 0 
                ? compareModified 
                : Long.compare(f2.length(), f1.length()); // the two files have the same last modified time,
                                                          // lets sort them by file size (biggest files first)
        })
        // get the name of the file
        .map(File::getName)
        // return the names from the sorted files in a String array
        .toArray(String[]::new);
}

Updated using Files.list(path) (the updated method now can throw an IOException):使用Files.list(path)更新(更新的方法现在可以抛出 IOException):

public static String[] sortFiles(File directory) throws IOException {
    return Files
        // get all the paths in the directory
        .list(directory.toPath())
        // turn paths into files
        .map(Path::toFile)
        // sortying them first by last modfied and then by length
        .sorted((f1, f2) -> {
            // the sorted function uses a comparotor or a function which compares two files
            // first compare the two files by last modified (newest files first => * -1)
            final int compareModified = Long.compare(f2.lastModified(), f1.lastModified());
            return compareModified != 0 
                ? compareModified 
                : Long.compare(f2.length(), f1.length()); // the two files have the same last modified time,
                                                          // lets sort them by file size (biggist first)
        })
        // get the name of the file
        .map(File::getName)
        // return the names from the sorted files in a String array
        .toArray(String[]::new);
}

Update 2 using only the nio file API.更新 2 仅使用nio文件 API。

Comparing Path s using Files.getLastModifiedTime and Files.size .使用Files.getLastModifiedTimeFiles.size比较Path I have to throw a RuntimeException when one of these methods throws an IOException because it is not possible to throw a (checked) exception from a lambda in a stream (which also would not be possible in the compare method of a Comparator<Path> ).当这些方法之一抛出IOException时,我必须抛出RuntimeException ,因为不可能从流中的 lambda 抛出(已检查)异常(这在Comparator<Path>compare方法中也是不可能的) .

import java.io.IOException;
import java.nio.file.Files;
import java.nio.file.Path;
import java.nio.file.Paths;

// run : sortFiles(Paths.get("/foo/bar/"))
public static String[] sortFiles(Path directory) throws IOException {
    return Files
        .list(directory)
        .sorted((p1, p2) -> {
            try {
                final int compareModified = Files.getLastModifiedTime(p2).compareTo(Files.getLastModifiedTime(p1));
                return compareModified != 0
                    ? compareModified
                    : Long.compare(Files.size(p2), Files.size(p1));
            } catch (IOException ex) {
                throw new RuntimeException(ex);
            }
        })
        .map(Path::getFileName)
        .map(Path::toString)
        .toArray(String[]::new);
}

I threw together a little demo with lambdas我用 lambdas 拼凑了一个小演示

public static void main(String[] args) {

    File f = new File(System.getProperty("user.home") + "/temp");

    List<File> files = Arrays.asList(f.listFiles(((dir, name) -> !(new File(dir,name)).isDirectory())));

    System.out.println("****** Listing as received *********** ");
    files.forEach(file -> System.out.println(file.getName()));

    System.out.println("****** Listing sorted by length *********** ");
    files.sort((f1,f2) -> Long.compare(f1.length(),f2.length()));
    files.forEach(file -> System.out.println(
          String.format("%-30s length = %2d",file.getName(),file.length())));

    System.out.println("****** Listing sorted by date **************");
    files.sort((f1,f2) -> Long.compare(f1.lastModified(),f2.lastModified()));
    files.stream()
          .map(file -> String.format("%-30s date mod = %2$td-%2tm-%2$tY %2$tH:%2$tM:%2$ts",file.getName(), new Date(file.lastModified())))
          .collect(Collectors.toList()).forEach(System.out::println);
}

The generated output生成的输出

****** Listing as received *********** 
.DS_Store
allclasses-frame.html
allclasses-noframe.html
alltext_awesome.test
alltext_java8.test
alltext_oldjava.text
bigDbTesting.mv.db
bigDbTesting.trace.db
constant-values.html
cx_d_entity_npn.txt
default-centos-66-pmd1.box
deprecated-list.html
F_TXN_Refresh.SFS.kjb
fakedata.mv.db
faker.mv.db
help-doc.html
index.html
jdk160_26.zip
keepPass_v0.xml
ldapinfo.txt
overview-frame.html
overview-summary.html
overview-tree.html
package-list
script.js
simpleDbToFileTest.txt
simpleDbToFileTest2.txt
stringIncrementer.jar
stylesheet.css
table.csv
temp.sql
those.enc.copy.properties
those.enc.properties
those.properties
untitled text 4.txt
untitled text.txt
untitled text111.txt
****** Listing sorted by length *********** 
cx_d_entity_npn.txt            length =  0
package-list                   length = 20
untitled text 4.txt            length = 39
untitled text111.txt           length = 132
simpleDbToFileTest.txt         length = 180
ldapinfo.txt                   length = 295
untitled text.txt              length = 695
script.js                      length = 827
overview-frame.html            length = 850
those.enc.copy.properties      length = 853
those.enc.properties           length = 853
allclasses-noframe.html        length = 1243
allclasses-frame.html          length = 1343
temp.sql                       length = 1504
those.properties               length = 1836
bigDbTesting.trace.db          length = 2673
index.html                     length = 2863
simpleDbToFileTest2.txt        length = 3201
deprecated-list.html           length = 3514
constant-values.html           length = 3564
overview-summary.html          length = 4043
alltext_awesome.test           length = 4546
alltext_java8.test             length = 4546
alltext_oldjava.text           length = 4546
overview-tree.html             length = 4821
F_TXN_Refresh.SFS.kjb          length = 7254
help-doc.html                  length = 8242
stringIncrementer.jar          length = 12243
.DS_Store                      length = 12292
stylesheet.css                 length = 12808
keepPass_v0.xml                length = 14810
faker.mv.db                    length = 28672
table.csv                      length = 47820
bigDbTesting.mv.db             length = 212992
fakedata.mv.db                 length = 75051008
jdk160_26.zip                  length = 87253361
default-centos-66-pmd1.box     length = 20131307999
****** Listing sorted by date **************
jdk160_26.zip                  date mod = 04-04-2014 10:09:1396620572
simpleDbToFileTest2.txt        date mod = 02-07-2014 14:07:1404324435
simpleDbToFileTest.txt         date mod = 03-07-2014 08:05:1404389127
cx_d_entity_npn.txt            date mod = 23-09-2014 15:39:1411501165
F_TXN_Refresh.SFS.kjb          date mod = 23-09-2014 16:17:1411503474
keepPass_v0.xml                date mod = 21-10-2014 16:48:1413924527
ldapinfo.txt                   date mod = 22-10-2014 10:39:1413988799
untitled text111.txt           date mod = 08-12-2014 09:05:1418047503
default-centos-66-pmd1.box     date mod = 03-02-2015 10:56:1422978975
untitled text 4.txt            date mod = 06-02-2015 23:14:1423282475
untitled text.txt              date mod = 06-02-2015 23:14:1423282475
stringIncrementer.jar          date mod = 13-02-2015 18:19:1423869592
fakedata.mv.db                 date mod = 19-02-2015 08:31:1424352716
faker.mv.db                    date mod = 24-03-2015 14:49:1427222991
table.csv                      date mod = 30-04-2015 10:07:1430402823
bigDbTesting.mv.db             date mod = 30-04-2015 10:33:1430404409
bigDbTesting.trace.db          date mod = 30-04-2015 10:43:1430405015
.DS_Store                      date mod = 27-05-2015 09:28:1432733304
alltext_awesome.test           date mod = 08-06-2015 08:51:1433767887
alltext_java8.test             date mod = 08-06-2015 08:51:1433767887
alltext_oldjava.text           date mod = 08-06-2015 08:51:1433767887
stylesheet.css                 date mod = 08-06-2015 10:24:1433773446
package-list                   date mod = 08-06-2015 10:25:1433773522
script.js                      date mod = 08-06-2015 10:25:1433773522
overview-frame.html            date mod = 08-06-2015 10:25:1433773522
allclasses-noframe.html        date mod = 08-06-2015 10:25:1433773522
allclasses-frame.html          date mod = 08-06-2015 10:25:1433773522
index.html                     date mod = 08-06-2015 10:25:1433773522
deprecated-list.html           date mod = 08-06-2015 10:25:1433773522
constant-values.html           date mod = 08-06-2015 10:25:1433773522
overview-summary.html          date mod = 08-06-2015 10:25:1433773522
overview-tree.html             date mod = 08-06-2015 10:25:1433773522
help-doc.html                  date mod = 08-06-2015 10:25:1433773522
temp.sql                       date mod = 08-06-2015 15:21:1433791297
those.properties               date mod = 11-06-2015 14:33:1434047622
those.enc.copy.properties      date mod = 11-06-2015 15:38:1434051531
those.enc.properties           date mod = 11-06-2015 15:49:1434052178

Easiest way is :最简单的方法是:

import org.apache.commons.io
import java.util.Arrays;

then然后

File directory = new File(".");
File[] files = directory.listFiles((FileFilter) FileFileFilter.FILE);
Arrays.sort(files, LastModifiedFileComparator.LASTMODIFIED_COMPARATOR);
Arrays.sort(files, LastModifiedFileComparator.LASTMODIFIED_REVERSE);

other comparators available in that library:该库中可用的其他比较器:

CompositeFileComparator, DefaultFileComparator, DirectoryFileComparator, ExtensionFileComparator, NameFileComparator, PathFileComparator, SizeFileComparator. CompositeFileComparator、DefaultFileComparator、DirectoryFileComparator、ExtensionFileComparator、NameFileComparator、PathFileComparator、SizeFileComparator。

Even this post already has an absolutly correct answer, I've tried to do all things without old Java IO Package things, using only NIO features for performance issues.即使这篇文章已经有一个绝对正确的答案,我也尝试在没有旧的 Java IO Package 的情况下做所有事情,只使用 NIO 功能来解决性能问题。 So here it is (sorts descending).所以这里是(按降序排列)。 I don't know if it is available in Android, but in Java 8 it is.我不知道它是否在 Android 中可用,但在 Java 8 中是。 (Based on things from Peter Neyens solution). (基于 Peter Neyens 解决方案中的内容)。 This solution is based on an other question from me Why does the java DirectoryStream perform so slow?此解决方案基于我的另一个问题为什么 java DirectoryStream 执行如此缓慢?

import java.io.IOException;
import java.io.UncheckedIOException;
import java.nio.file.Files;
import java.nio.file.Path;
import java.nio.file.Paths;

public class FileSorter2 {

  public String[] getSortedFileList(Path dir) throws IOException {
    return Files.list(dir).map(PathInfo::new).sorted().map(p -> p.
            getFileName()).toArray(String[]::new);
  }

  public static void main(String[] args) throws IOException {
    // some testing, this main throws IOException
    Path dir = Paths.get("C:\\Windows\\system32");

    FileSorter2 fs = new FileSorter2();
    long before = System.currentTimeMillis();
    String[] sortedFileNames = fs.getSortedFileList(dir);
    long after = System.currentTimeMillis();
    System.out.println("Time needed: " + (after - before));

  }

  // Helping class to cache object which is compared
  static class PathInfo implements Comparable<PathInfo> {

    private final String fileName;
    private final long modified;
    private final long size;

    public PathInfo(Path path) {
      try {
        fileName = path.getFileName().toString();
        modified = Files.getLastModifiedTime(path).toMillis();
        size = Files.size(path);
      } catch (IOException ex) {
        throw new UncheckedIOException(ex);
      }
    }

    @Override
    public int compareTo(PathInfo o) {
      int cmp = Long.compare(modified, o.modified);
      if (cmp == 0) {
        cmp = Long.compare(size, o.size);
      }
      return cmp;
    }

    public String getFileName() {
      return fileName;
    }
  }
}

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM