繁体   English   中英

Java Arraylist of object 按日期从 ZEB3A834246F50C9BDE2C825D7450

[英]Java Arraylist of object remove elements from an arraylist by date

这是我的 arraylist

ArrayList<Courses> list = new ArrayList<Courses>();
list.add( new Courses(350,5/20/2020) );
list.add( new Courses(350,4/20/2019 );
list.add( new Courses(350,3/20/2018) );
list.add( new Courses(360,6/20/2020) );
list.add( new Courses(360,5/20/2019) );
list.add( new Courses(370,5/20/2020) );
list.add( new Courses(370,5/19/2018) );
list.add( new Courses(360,4/10/2016) );

public class Courses{
 int coursenum;
 Date date;

}

如何删除元素以使 arraylist 仅包含具有最新日期的元素?

应该喜欢这个;

350, 5/20/2020}
360,6/20/2020}
370, 5/20/2020

定义关键日期并删除日期在关键日期之前的所有课程。 如果您有适当的吸气剂:

ArrayList<Courses> list = new ArrayList<Courses>();
//populate list

Date someDate = new SimpleDateFormat("MM/dd/yyyy").parse("01/01/2020");

list.removeIf(c -> c.getDate().before(someDate));

请@Randy Casburn 写了一个最小但完整的示例,我不想向感兴趣的读者隐瞒:

/**
 *
 * @author Randy Casburn
 */
import java.util.ArrayList;
import java.util.Date;
import java.util.List;

public class Main {

    public static void main(String[] args) {

        Date latest = new Date("1/1/2020");
        List<Courses> list = new ArrayList<>();
        list.add(new Courses(350, new Date("5/20/2020")));
        list.add(new Courses(350, new Date("4/20/2019")));
        list.add(new Courses(350, new Date("3/20/2018")));
        list.add(new Courses(360, new Date("6/20/2020")));
        list.add(new Courses(360, new Date("5/20/2019")));
        list.add(new Courses(370, new Date("5/20/2020")));
        list.add(new Courses(370, new Date("5/19/2018")));
        list.add(new Courses(360, new Date("4/10/2016")));

        list.removeIf(course -> !course.date.after(latest));
        list.forEach(l-> System.out.println(l.date));
    }
}

class Courses {
    int coursenum;
    Date date;
    Courses(int coursenum, Date date){
        this.coursenum = coursenum;
        this.date = date;
    }

}

我会推荐使用 java-8 中的LocalDate ,因为Date是旧版本

public class Courses{
    int coursenum;
    LocalDate date;

  }

然后你可以使用removeIf

list.removeIf(d->d.isBefore(LocalDate.now());

Java 1.7 和 java.time 通过 ThreeTen Backport

    ArrayList<Course> list = new ArrayList<>();
    list.add( new Course(350, "5/20/2020") );
    list.add( new Course(350, "4/20/2019") );
    list.add( new Course(350, "3/20/2018") );
    list.add( new Course(360, "6/20/2020") );
    list.add( new Course(360, "5/20/2019") );
    list.add( new Course(370, "5/20/2020") );
    list.add( new Course(370, "5/19/2018") );
    list.add( new Course(360, "4/10/2016") );
    
    // Find latest date for each course number
    Map<Integer, LocalDate> latestDates = new HashMap<>();
    for (Course currentCourse : list) {
        LocalDate latestHitherto = latestDates.get(currentCourse.getCourseNumber());
        if (latestHitherto == null || currentCourse.getDate().isAfter(latestHitherto)) {
            latestDates.put(currentCourse.getCourseNumber(), currentCourse.getDate());
        }
    }
    
    // Remove courses that haven’t got the latest date
    Iterator<Course> courseIterator = list.iterator();
    while (courseIterator.hasNext()) {
        Course currentCourse = courseIterator.next();
        if (currentCourse.getDate().isBefore(latestDates.get(currentCourse.getCourseNumber()))) {
            courseIterator.remove();
        }
    }
    
    // Print result
    for (Course currentCourse : list) {
        System.out.format("%3d %s%n", 
                currentCourse.getCourseNumber(), 
                currentCourse.getDate().format(Course.dateFormatter));
    }

此片段中的 Output 是:

 350 5/20/2020 360 6/20/2020 370 5/20/2020

我在 jdk1.7.0_67 上运行。 我添加了 ThreeTen Backport 1.3.6。 请参阅下面的链接。

这是我使用的Course class:

public class Course {
    
    public static final DateTimeFormatter dateFormatter
            = DateTimeFormatter.ofPattern("M/d/u");
    
    private int courseNumber;
    private LocalDate date;
    
    public Course(int courseNumber, String dateString) {
        this.courseNumber = courseNumber;
        this.date = LocalDate.parse(dateString, dateFormatter);
    }

    public int getCourseNumber() {
        return courseNumber;
    }

    public LocalDate getDate() {
        return date;
    }
}

如果您坚持使用java.util.Date — 一个设计不良且早已过时的 class — (1) 我不明白您为什么要这样做,(2) 您可以修改我的代码以使用Date代替。

Stream版

您可能需要考虑升级您的 Java 版本。 Java 15 已经发布,Java 16 的早期访问版本已经在 Java 8 来流。 它们将允许您以更少的代码行获得相同的结果:

    Collection<Course> filteredCourses = list.stream()
            .collect(Collectors.groupingBy(Course::getCourseNumber,
                    Collectors.collectingAndThen(Collectors.maxBy(Comparator.comparing(Course::getDate)),
                            Optional::orElseThrow)))
            .values();
    List<Course> filteredList = new ArrayList<>(filteredCourses);
    filteredList.forEach(c -> System.out.format(
            "%3d %s%n", c.getCourseNumber(), c.getDate().format(Course.dateFormatter)));
 370 5/20/2020 360 6/20/2020 350 5/20/2020

就代码而言,它在结果列表中没有给出相同的课程顺序,并且它需要 Java 10(那里引入了重载的 no-arg orElseThrow方法)。 即使您需要相同的订单,流仍然会非常有用。

问:这可以在 Java 1.7 上工作吗?

java.time 适用于较旧和较新的 Android 设备。 它只需要至少Java 6

  • 在 Java 8 及更高版本以及更新的 Android 设备(来自 API 级别 26)中,现代 ZDB9734A 内置了23871083ACE16。
  • 在非 Android Java 6 和 7 中,获得 ThreeTen Backport,现代类的后向端口(JSR 310 的 ThreeTen;参见底部的链接)。
  • 在较旧的 Android 上,要么使用去糖,要么使用 ThreeTen Backport 的 Android 版本。 它被称为 ThreeTenABP。 在后一种情况下,请确保从带有子包的org.threeten.bp导入日期和时间类。

链接

我附上我的代码作为您要求的想法。 你可以玩弄它。

public class Courses {

    int courseNum;

    LocalDate date;

    public Courses(int courseNum, LocalDate date) {
        this.courseNum = courseNum;
        this.date = date;
    }

    public int getCourseNum() {
        return courseNum;
    }

    public void setCourseNum(int courseNum) {
        this.courseNum = courseNum;
    }

    public LocalDate getDate() {
        return date;
    }

    public void setDate(LocalDate date) {
        this.date = date;
    }

    @Override public String toString() {
        return new StringJoiner(", ", Courses.class.getSimpleName() + "[", "]")
                .add("courseNum=" + courseNum)
                .add("date=" + date)
                .toString();
    }

public class Main {
  public static void main(String[] args) {
        List<Courses> list = new ArrayList<>();
        list.add(new Courses(350, LocalDate.of(2020, 5, 20)));
        list.add(new Courses(350, LocalDate.of(2019, 4, 20)));
        list.add(new Courses(350, LocalDate.of(2018, 3, 20)));
        list.add(new Courses(360, LocalDate.of(2020, 6, 20)));
        list.add(new Courses(360, LocalDate.of(2019, 5, 20)));
        list.add(new Courses(370, LocalDate.of(2020, 5, 20)));
        list.add(new Courses(370, LocalDate.of(2018, 5, 19)));
        list.add(new Courses(360, LocalDate.of(2016, 4, 10)));

        List<Courses> res = list.stream().filter(c -> c.getDate().getYear() == 2020).collect(Collectors.toList());

        res.forEach(System.out::println);
    }

暂无
暂无

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

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