当前位置: 首页 > 知识库问答 >
问题:

Java 8分组为对象集合

邹桐
2023-03-14

我想在到期日对一个Retrient对象集合进行分组,但我想为每个组创建一个新的RentalReport对象,其中键是预定义的值(枚举),并且组是该对象的属性。我通过根据每个条件拟合集合并为每个条件创建一个RentalReport对象来实现这一点,但我想知道是否可以使用Collectors类的groupingBy方法来实现这一点。

有没有可能在Java 8中按一组预定义的过滤器进行分组,这样我就可以创建一个映射,其中键是枚举,值是租赁对象的集合。然后我可以迭代这个映射并生成RentalReport对象。

我已经创建了这个演示,但真正的任务涉及多个group by子句,所以如果我可以通过分组来实现这一点就太好了。

    import java.util.ArrayList;
import java.util.Arrays;
import java.util.List;
import java.util.stream.Collectors;
import org.joda.time.DateTime;

public class TestGrouping {

    enum RentalClassification {
        UNRESTRICTED, //No restriction restricted=false
        OVERDUE,      //todays date after due date.
        NEARLY_OVERDUE, // todays date after due date + 2 days
        NOT_OVERDUE
    }

    public static void main(String[] args) {

        class Rental {
            Integer rentalId;
            Integer productId;
            boolean restricted;
            DateTime dueDate;

            public Rental(Integer rentalId, Integer productId, boolean restricted, DateTime dueDate){
                this.rentalId = rentalId;
                this.productId = productId;
                this.restricted = restricted;
                this.dueDate = dueDate;
            }

            public Integer getRentalId() {
                return rentalId;
            }

            public void setRentalId(Integer rentalId) {
                this.rentalId = rentalId;
            }

            public Integer getProductId() {
                return productId;
            }

            public void setProductId(Integer productId) {
                this.productId = productId;
            }

            public boolean isRestricted() {
                return restricted;
            }

            public void setRestricted(boolean restricted) {
                this.restricted = restricted;
            }

            public DateTime getDueDate() {
                return dueDate;
            }

            public void setDueDate(DateTime dueDate) {
                this.dueDate = dueDate;
            }

            public String toString(){
                return "RentalId:"+this.rentalId+". ProductId:"+this.productId+". Due date:"+this.dueDate+". -";
            }
        }

        class RentalReport {

            RentalClassification classification;
            List<Rental> rentals;

            public RentalReport(RentalClassification classification, List<Rental> rentals) {
                this.classification = classification;
                this.rentals = rentals;
            }

            public RentalClassification getClassification() {
                return classification;
            }
            public void setClassification(RentalClassification classification) {
                this.classification = classification;
            }
            public List<Rental> getRentals() {
                return rentals;
            }
            public void setRentals(List<Rental> rentals) {
                this.rentals = rentals;
            }

            public String toString(){
                StringBuilder sb = new StringBuilder("Classification:"+this.classification.name()+". Rental Ids:");
                this.rentals.forEach(r -> sb.append(r.getRentalId()));
                return sb.toString();

            }

        }

        DateTime today = new DateTime();

        List<Rental> rentals = Arrays.asList(
                new Rental(1,100, true, today.plusDays(-10)),
                new Rental(2,101, false, today.plusDays(-10)),
                new Rental(3,102, true, today.plusDays(-4)),
                new Rental(4,103, true, today.plusDays(-4)),
                new Rental(5,104, true, today.plusDays(-4)),
                new Rental(6,105, true, today.plusDays(2)),
                new Rental(7,106, true, today.plusDays(2)),
                new Rental(8,107, true, today.plusDays(2)),
                new Rental(9,108, true, today.plusDays(4)),
                new Rental(10,109, true, today.plusDays(5))
                );


        List<RentalReport> rentalReports = new ArrayList<RentalReport>();

        List<Rental> unrestrictedRentals = rentals.stream()
                                           .filter(r -> !r.isRestricted())
                                           .collect(Collectors.toList());

        rentalReports.add(new RentalReport(RentalClassification.UNRESTRICTED, unrestrictedRentals));

        List<Rental> overdueRentals = rentals.stream()
                                      .filter(r -> r.isRestricted() && r.getDueDate().isBefore(new DateTime()))
                                      .collect(Collectors.toList());

        rentalReports.add(new RentalReport(RentalClassification.OVERDUE, overdueRentals));

        List<Rental> nearlyOverdueRentals = rentals.stream()
                                            .filter(r -> r.isRestricted() 
                                                    && r.getDueDate().isAfter(new DateTime())
                                                    && r.getDueDate().isBefore(new DateTime().plusDays(2)))
                                            .collect(Collectors.toList());

        rentalReports.add(new RentalReport(RentalClassification.NEARLY_OVERDUE, nearlyOverdueRentals));

        List<Rental> notOverdueRentals = rentals.stream()
                                        .filter(r -> r.isRestricted() && r.getDueDate().isAfter(new DateTime()))
                                        .collect(Collectors.toList());

        rentalReports.add(new RentalReport(RentalClassification.NOT_OVERDUE, notOverdueRentals));

        System.out.println("Rental Reports: "+rentalReports.toString());

    }
    }

共有1个答案

梁丘赞
2023-03-14

来点这样的怎么样:

rentals.stream().collect(Collectors.groupingBy(r -> {
    if (!r.isRestricted()) {
        return RentalClassification.UNRESTRICTED;
    }
    if (r.isRestricted() && r.getDueDate().isBefore(new DateTime())) {
        return RentalClassification.OVERDUE;
    }
    // and so on
}));

可能还值得将lambda作为方法RentalClassificationgetRentalClassification()添加到Retric中

 类似资料:
  • 问题内容: Java 8中有什么方法可以将一个元素分组而不收集它们?我希望结果再次出现。因为我必须处理大量数据甚至是无限流,所以我无法先收集数据并再次流处理结果。 所有需要分组的元素在第一流中都是连续的。因此,我喜欢使流评估保持懒惰。 问题答案: 无法使用标准Stream API做到这一点。通常,您无法执行此操作,因为将来总是有可能出现属于任何已创建组的新项目,因此,在处理所有输入之前,您无法将组

  • 在Java8中有什么方法可以在中分组元素而不收集它们吗?我希望结果再次成为。因为我必须处理大量的数据,甚至是无限的流,所以我不能首先收集数据,然后再次流化结果。 所有需要分组的元素在第一个流中是连续的。因此,我喜欢保持流评估懒惰。

  • 问题内容: 如果我运行,Laravel会执行以下烦人的事情,即向集合中的每个模型添加键,如下所示: 我如何摆脱“ 4”和“ 7”,所以它是我的对象的数组? 我运行的代码是: 问题答案: 问题在于该方法不会为基础集合数组重新设置密钥。因此,Collection仍表示一个数组,只是您的数组看起来像这样: 尽管这在PHP中是一个非常有效的数组,但在JSON中却不是一个合适的数组。由于无法将其表示为JSO

  • 我对Java8相当陌生。我需要将普通对象列表转换为按特定标准分组并在用户界面上显示。 地图的关键应该是“fromDate-todate”的组合,学生名单应该与此组合相关联 此外,“ClassOfMSWAN”对象需要转换为“Student”对象并保存到列表中 Java1的代码。7已编写,需要转换为Java1。八, 请帮帮我。

  • 如果两个集合包含相同的对象,如何进行比较? 当然会打印错误。