将多个字段置于一个字符串中,然后使用集合来分组以查找每个组的总和

发布于 2025-01-29 18:37:18 字数 418 浏览 3 评论 0 原文

想象一下,我有以下字段:

>  String name1
>  String name2
>  String name3
>  BigDecimal amount

我想使用一个 String 对它们进行分组,这是Name1,Name2和Name3的串联。

例如:

name1 = hi
name2 = am
name3 = sarah

String newString = hiamsarah

然后,在通过链式字符串设法将对象分组后,我想获得每个组的字段的总和。

这可能吗?

我已经尝试了任何可能的方法,但是我无法通过它。另外,我是收藏品的新手。

Imagine I have the following fields:

>  String name1
>  String name2
>  String name3
>  BigDecimal amount

I want to group them by using one String which is the concatenation of name1, name2 and name3.

For example:

name1 = hi
name2 = am
name3 = sarah

String newString = hiamsarah

Then, after I manage to group the objects by the chained String, I want to get the overall sum of the amount field for each group.

Is this possible?

I've tried any possible way, but I just can't get through it. Also, I'm kind of new to collections.

如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。

扫码二维码加入Web技术交流群

发布评论

需要 登录 才能够评论, 你可以免费 注册 一个本站的账号。

评论(2

薄荷→糖丶微凉 2025-02-05 18:37:18

假设您的实例包含在 list 中,并且在您的类中,有一种返回链式名称的方法,您可以使用终端操作收集来使用集合流和组。 (collectors.tomap())

链式值可以用作密钥, bigdecimal 值作为对应于密钥的值,最后可以通过求和 bigdecimal 值来处理碰撞案例。

由于您没有提供所指的类的代码,因此我声明了一个名为 myClass 包含3 字符串字段和 bigdecimal 的类。代码>。这是代码的片段:

public class Main {
    public static void main(String[] args) {
        List<MyClass> list = new ArrayList<>(List.of(
                new MyClass("I", "am", "Sarah", BigDecimal.valueOf(5.33)),
                new MyClass("I", "am", "Frank", BigDecimal.valueOf(2.75)),
                new MyClass("I", "am", "Sarah", BigDecimal.valueOf(3.56)),
                new MyClass("I", "am", "Frank", BigDecimal.valueOf(7.12)),
                new MyClass("I", "am", "John", BigDecimal.valueOf(1.11))
        ));

        Map<String, BigDecimal> mapRes = list.stream()
                .collect(Collectors.toMap(mc -> mc.chainNames(), mc -> mc.getAmount(), (decimal1, decimal2) -> decimal1.add(decimal2)));

        System.out.println(mapRes);
    }
}

测试类实现( myClass ):

class MyClass {
    private String name1;
    private String name2;
    private String name3;
    private BigDecimal amount;

    public MyClass(String name1, String name2, String name3, BigDecimal amount) {
        this.name1 = name1;
        this.name2 = name2;
        this.name3 = name3;
        this.amount = amount;
    }

    /* ... your implementation ...*/

    public BigDecimal getAmount() {
        return amount;
    }

    public String chainNames() {
        StringBuilder strBld = new StringBuilder(name1);
        strBld.append(name2);
        strBld.append(name3);
        return strBld.toString();
    }
}

这里还有一个链接来测试代码:

https://ideone.com/il1zq8

Supposing that your instances are contained within a List and that within your class there is a method to return the chained names, you could use the collection stream and group by your instances with the terminal operation collect(Collectors.toMap()).

The chained value can be used as the key, the BigDecimal value as the value corresponding to the key and finally the collision cases can be handled by summing the BigDecimal values.

Since you didn't provide the code of the class you're referring to, I declared a class named MyClass containing the 3 String fields and the BigDecimal. Here is a snippet of the code:

public class Main {
    public static void main(String[] args) {
        List<MyClass> list = new ArrayList<>(List.of(
                new MyClass("I", "am", "Sarah", BigDecimal.valueOf(5.33)),
                new MyClass("I", "am", "Frank", BigDecimal.valueOf(2.75)),
                new MyClass("I", "am", "Sarah", BigDecimal.valueOf(3.56)),
                new MyClass("I", "am", "Frank", BigDecimal.valueOf(7.12)),
                new MyClass("I", "am", "John", BigDecimal.valueOf(1.11))
        ));

        Map<String, BigDecimal> mapRes = list.stream()
                .collect(Collectors.toMap(mc -> mc.chainNames(), mc -> mc.getAmount(), (decimal1, decimal2) -> decimal1.add(decimal2)));

        System.out.println(mapRes);
    }
}

Test class implementation (MyClass):

class MyClass {
    private String name1;
    private String name2;
    private String name3;
    private BigDecimal amount;

    public MyClass(String name1, String name2, String name3, BigDecimal amount) {
        this.name1 = name1;
        this.name2 = name2;
        this.name3 = name3;
        this.amount = amount;
    }

    /* ... your implementation ...*/

    public BigDecimal getAmount() {
        return amount;
    }

    public String chainNames() {
        StringBuilder strBld = new StringBuilder(name1);
        strBld.append(name2);
        strBld.append(name3);
        return strBld.toString();
    }
}

Here there is also a link to test the code:

https://ideone.com/IL1ZQ8

别再吹冷风 2025-02-05 18:37:18
  1. 要连接多个字符串,有方法 string.join(“”,NAME1,NAME2,NAME3)
  2. 按列表中的某些值分组,并汇总某个值,应与 collectors.groupingbyby 一起使用。 + collector.reducing

假设给定类是记录自Java 14以来提供了以下实现:

public static void main(String[] args) {
    record MyObj(String name1, String name2, String name3, BigDecimal amount) {
        public String fullName() {
            return String.join("", name1, name2, name3);
        }
    };
    
    List<MyObj> list = List.of(
            new MyObj("I", "am", "Sarah", BigDecimal.valueOf(5.33)),
            new MyObj("I", "am", "Frank", BigDecimal.valueOf(2.75)),
            new MyObj("I", "am", "Sarah", BigDecimal.valueOf(3.56)),
            new MyObj("I", "am", "Frank", BigDecimal.valueOf(7.12)),
            new MyObj("I", "am", "John",  BigDecimal.valueOf(1.11))
    );

    Map<String, BigDecimal> mapRes = list.stream()
            .collect(Collectors.groupingBy(
                MyObj::fullName, 
                Collectors.reducing(BigDecimal.ZERO, MyObj::amount, BigDecimal::add)
            ));

    System.out.println(mapRes);
}

输出:输出:

{IamJohn=1.11, IamSarah=8.89, IamFrank=9.87}
  1. To concatenate multiple strings, there is method String::join, the first argument is a delimiter which can be an empty string String.join("", name1, name2, name3)
  2. To group by some values in a list and summarize a certain value, Stream API should be used with Collectors.groupingBy + Collectors.reducing

Assuming that the given class is implemented as a record provided since Java 14, the following implementation is offered:

public static void main(String[] args) {
    record MyObj(String name1, String name2, String name3, BigDecimal amount) {
        public String fullName() {
            return String.join("", name1, name2, name3);
        }
    };
    
    List<MyObj> list = List.of(
            new MyObj("I", "am", "Sarah", BigDecimal.valueOf(5.33)),
            new MyObj("I", "am", "Frank", BigDecimal.valueOf(2.75)),
            new MyObj("I", "am", "Sarah", BigDecimal.valueOf(3.56)),
            new MyObj("I", "am", "Frank", BigDecimal.valueOf(7.12)),
            new MyObj("I", "am", "John",  BigDecimal.valueOf(1.11))
    );

    Map<String, BigDecimal> mapRes = list.stream()
            .collect(Collectors.groupingBy(
                MyObj::fullName, 
                Collectors.reducing(BigDecimal.ZERO, MyObj::amount, BigDecimal::add)
            ));

    System.out.println(mapRes);
}

Output:

{IamJohn=1.11, IamSarah=8.89, IamFrank=9.87}
~没有更多了~
我们使用 Cookies 和其他技术来定制您的体验包括您的登录状态等。通过阅读我们的 隐私政策 了解更多相关信息。 单击 接受 或继续使用网站,即表示您同意使用 Cookies 和您的相关数据。
原文