你可以使用函子/函数式编程来对Java 7中的列表进行分组(并计算每个组的元素)? [英] Can you use a functor/functional programming to group a list in Java 7 (and count its elements per group)?

查看:498
本文介绍了你可以使用函子/函数式编程来对Java 7中的列表进行分组(并计算每个组的元素)?的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

你可以分组列表< TypeEnum>类型=新的ArrayList(Arrays.asList(TypeEnum.A,TypeEnum.B,TypeEnum.A)); Map< TypeEnum,Integer> countPerType; ,使用函子(例如谷歌的番石榴,< apache href =https://commons.apache.org/proper/commons-functor/ =nofollow noreferrer> Apache的Commons Functor ) pre Java 8?



我试图让我的脑海围绕函数式编程,但我不确定这样的事情实际上是否可能(因为我不只是映射集合值,而是尝试在聚合中)?

在命令式风格中,我会做这样的事情:

  public Map< TypeEnum,Integer> countByGroup(List< TypeEnum>类型){
Map< TypeEnum,Integer> countingTypes = new HashMap<>(); (TypeEnum类型:类型){
if(countingTypes.containsKey(type)){
countingTypes.put(type,countedTypes.get(type)+ 1)
;
} else {
countingTypes.put(type,1);
}
}
返回countingTypes;
}



编辑:依赖副作用看起来有点不合适 - 或者它是如何完成的......?

 过程< TypeEnum> count = new Procedure< TypeEnum>(){
public Map< TypeEnum,Integer> countPerType = null;

@Override
public void run(TypeEnum type){
if(countPerType.containsKey(type)){
countPerType.put(type,countPerType.get类型)+ 1);
} else {
countPerType.put(type,1);
}
}

public Procedure< TypeEnum> init(Map< TypeEnum,Integer> countPerType){
this.countPerType = countPerType;
返回此;
}
} .init(countPerType); // kudos http://stackoverflow.com/a/12206542/2018047


解决方案 div>

OlivierGrégoire 评论正确答案: p>


使用Guava,您需要一个简单的 Multiset ,更具体地说它的 EnumMultiset Multiset 是一个数据结构,用于跟踪计数的元素。


您的列表< TypeEnum>类型,您可以使用 EnumMultiset docs / com / google / common / collect / EnumMultiset.html#create-java.lang.Iterable-rel =nofollow noreferrer> create : / p>

  Multiset< TypeEnum> multiset = EnumMultiset.create(types); 

您可以查询 Multiset code>使用 count

  multiset.count(TypeEnum.A); // 2 
multiset.count(TypeEnum.B); // 1


Can you group List<TypeEnum> types = new ArrayList(Arrays.asList(TypeEnum.A, TypeEnum.B, TypeEnum.A)); into a Map<TypeEnum, Integer> countPerType;, using functors (e.g. Google's Guava, Apache's Commons Functor) pre Java 8?

I'm trying to get my head around functional programming, but am unsure if that sort of thing would actually be possible (as I'm not just mapping a collections value, but trying to aggregate)?

In imperative style, I would have done something like this:

public Map<TypeEnum, Integer> countByGroup(List<TypeEnum> types) {
    Map<TypeEnum, Integer> countedTypes = new HashMap<>();
    for(TypeEnum type : types) {
        if(countedTypes.containsKey(type)) {
            countedTypes.put(type, countedTypes.get(type) + 1);
        } else {
            countedTypes.put(type, 1);
        }
    }
    return countedTypes;
}


EDIT: Relying on side effects seems somewhat inappropriate - or is that how it's done...?

Procedure<TypeEnum> count = new Procedure<TypeEnum>() {
public Map<TypeEnum, Integer> countPerType = null;

    @Override
    public void run(TypeEnum type) {
        if(countPerType.containsKey(type)) {
            countPerType.put(type, countPerType.get(type) + 1);
        } else {
            countPerType.put(type, 1);
        }
    }

    public Procedure<TypeEnum> init(Map<TypeEnum, Integer> countPerType) {
        this.countPerType = countPerType;
        return this;
    }
}.init(countPerType); // kudos http://stackoverflow.com/a/12206542/2018047

解决方案

Olivier Grégoire commented the correct answer:

Using Guava, you want a simple Multiset, and more specifically its EnumMultiset implementation. Multiset is a data structure made to keep track of counted elements.

Given your List<TypeEnum> types you can create an EnumMultiset using create:

Multiset<TypeEnum> multiset = EnumMultiset.create(types);

And you can query for the count of an element in the Multiset using count:

multiset.count(TypeEnum.A); // 2
multiset.count(TypeEnum.B); // 1

这篇关于你可以使用函子/函数式编程来对Java 7中的列表进行分组(并计算每个组的元素)?的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆