繁体   English   中英

MultiSet.Entry和泛型比较器

[英]Comparator for MultiSet.Entry and Generics

我需要一个用于番石榴MultiSet.Entry的比较器,以便首先按计数排序,然后按字符串排序。 但是,我遇到了编译器问题,并且我认为泛型错误了。

这样编译:

Comparator<Multiset.Entry<String>> comparator() {
    return Comparator.comparing(Multiset.Entry::getCount);
}

但是,这不是:

Comparator<Multiset.Entry<String>> comparator() {
    return Comparator.comparing(Multiset.Entry::getCount).thenComparing(Multiset.Entry::getElement);
}
Error: java: incompatible types: cannot infer type-variable(s) T,U
    (argument mismatch; invalid method reference
      method getCount in interface com.google.common.collect.Multiset.Entry cannot be applied to given types
        required: no arguments
        found: java.lang.Object
        reason: actual and formal argument lists differ in length)

如果我将比较器(例如一个字符串)组合在一起,那么我显然不会遇到类似的问题。

Comparator<String> comparator2() {
    return Comparator.comparing(String::length).thenComparing(String::toString);
}

我在这里想念的是什么,如何使它工作?

(注意:我知道番石榴可能有不同的方法,但是我想了解我遇到的问题。)

认为这是因为类型定位(Java推理的一种形式)与代码中使用的点功能编程一起工作的原因(您可以在Java文档中阅读有关目标类型的信息 ,特别是称为“ Target Types and Method Arguments )。

简而言之,如果我有这样的事情:

List<String> list = new List<>();

这里的目标类型是List<String>因此Java(8)认识到您要创建的新列表已分配给它,并且应该是List<String>类型,因此可以推断该类型,而不必指定类型参数。

最初编译的最简短的内容是:代码部分Comparator.comparing(Multiset.Entry::getCount); 返回Comparator<T>的类型,此结果立即分配给方法的返回类型(即方法的返回类型是目标类型)。 编译器可以推断类型,因为目标类型是方法comparator的返回类型,您已在方法签名中将其明确定义/捕获为Comparator<Multiset.Entry<String>> TComparator<T>因此,可以推断。

在第二段代码中(您不会编译并需要显式类型见证参数-方法调用中<>中的显式位),您正在使用链接方法的点运算符。 这意味着将第二部分thenComparing(Multiset.Entry::getElement)应用于第一部分Comparator.comparing(Multiset.Entry::getCount)

第二部分可以从目标类型推断类型,因为第二部分的结果是方法返回的结果,所以第二部分的目标类型类似于上面进行编译的情况-方法返回类型为捕获并定义,因此可以推断出这一点。

但是对于第一部分,目标类型是不确定的,因为没有将其分配给具有实际类型的某种类型。 根据Comparator API, Comparator<T>是该函数返回的内容,但是由于它不知道具体要分配给哪种类型,因此您需要提供类型见证并在返回时明确指定Comparator<T> T (在您的情况下)应为Multiset.Entry<String>

暂无
暂无

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

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