Java8,Lambda:用Lambda替换匿名内部类
我有一个包含以下内容的类:Java8,Lambda:用Lambda替换匿名内部类,java,lambda,java-8,Java,Lambda,Java 8,我有一个包含以下内容的类: List roles = ldapTemplate.search(baseDn, replaceFilter, sc, new AttributesMapper() { public Object mapFromAttributes(Attributes attrs) throws NamingException { retu
List roles = ldapTemplate.search(baseDn, replaceFilter, sc,
new AttributesMapper() {
public Object mapFromAttributes(Attributes attrs)
throws NamingException {
return attrs.get("cn").get();
}
});
IntelliJ告诉我用lambda替换匿名内部类。
所以我试着:
List roles = ldapTemplate.search(
baseDn, replaceFilter, sc,
(Attributes a) -> { return a.get("cn").get(); };
);
但是,我得到一个编译错误:
Error:(46, 50) java: incompatible types: inference variable T has incompatible bounds
equality constraints: java.lang.String
lower bounds: java.lang.Object
我找不到这个问题的解决办法。你有什么想法吗?试试这个(去掉多余的分号)
我有一种强烈的感觉,你没有在你的问题中发布准确的代码。比如,我不能用你发布的代码重现错误 然而,让我印象深刻的是你对原始类型的使用。如果原始代码如下所示:
List<String> roles = ldapTemplate.search(baseDn, replaceFilter, sc,
new AttributesMapper() {
public Object mapFromAttributes(Attributes attrs)
throws NamingException {
return attrs.get("cn").get();
}
});
现在,编译器将为您推断类型AttributesMapper
,并产生错误,因为lambda表达式返回的是Object
,而不是String
,因此无法实现AttributesMapper
接口
您可以通过插入类型转换来实现AttributesMapper
接口,或者通过使用原始类型列表
声明roles
来解决此问题。但是,使用类型转换将是更干净的方法(并且应该是唯一不会产生编译器警告的方法):
List roles=ldapTemplate.search(baseDn、replaceFilter、sc、,
a->(字符串)a.get(“cn”).get();
(我简化了表达式以补偿包含的类型转换,看起来好多了,不是吗?一个简单的azure存储实体解析器接口及其实现方法:
EntityResolver<String> orderNumberResolver = new EntityResolver<String>() {
@Override
public String resolve(String partitionKey, String rowKey, Date timeStamp,
HashMap<String, EntityProperty> properties, String etag) {
return properties.get("SomeColumnName").getValueAsString();
}
};
EntityResolver orderNumberResolver=new EntityResolver(){
@凌驾
公共字符串解析(字符串分区键、字符串行键、日期时间戳、,
HashMap属性,字符串etag){
返回properties.get(“SomeColumnName”).getValueAsString();
}
};
上述方法的λ为:
EntityResolver<String> orderNumberResolver = (
partitionKey, rowKey, timeStamp, properties, etag
) -> properties.get("SomeColumnName").getValueAsString();
EntityResolver orderNumberResolver=(
partitionKey、rowKey、时间戳、属性、etag
)->properties.get(“SomeColumnName”).getValueAsString();
从上面的例子可以清楚地看出,lambda足够聪明,可以根据其匿名内部类处理方法参数的类型,因此它使得重写方法的实现变得容易。希望这会有所帮助。下面的代码显示了使用匿名内部类获取学生比较器
private static final Comparator<StudentDto> studentScoreComparator = new Comparator<StudentDto>() {
@Override
public int compare(StudentDto s1, StudentDto s2) {
if (s2.getScore() < s1.getScore()) {
return 1;
}
return s2.getScore() == s1.getScore() ? 0 : 1;
}
};
private static final Comparator studentScoreComparator=new Comparator(){
@凌驾
公共整数比较(学生数据到s1,学生数据到s2){
if(s2.getScore()
使用java8amdsonar建议只包含一个方法的匿名内部类应该成为lambdas
可以按如下方式转换
private static final Comparator<StudentDto> studentScoreComparator = (s1, s2) -> {
if (s2.getScore() < s1.getScore()) {
return 1;
}
return s2.getScore() == s1.getScore() ? 0 : 1;
};
private static final Comparator studentScoreComparator=(s1,s2)->{
if(s2.getScore()
只有一个方法实现的匿名内部类可以
作为功能接口考虑,可以很容易地被视为lambda
表情
看起来lambda的返回值需要转换为
字符串。
。是(属性a)->(字符串)a.get(“cn”).get()一切正常。但我不明白为什么在我的内部类中,我返回一个对象,所有的东西都是好的,而不是lambda中的。我不确定,但它一定与类型推断有关。我刚刚在我的机器上做了一个简单的测试,它似乎不需要浇铸就可以工作。使用的Java版本是Java版本“1.8.0_05”Java(TM)SE运行时环境(build 1.8.0_05-b13)Java热点(TM)64位服务器VM(build 25.5-b02,混合模式)
?啊,额外的分号。您可以将此添加到您的答案中吗?'List roles=ldapTemplate.search(baseDn,replaceFilter,sc,(a)->a.get(“cn”).get();'即使这样也应该行得通
EntityResolver<String> orderNumberResolver = (
partitionKey, rowKey, timeStamp, properties, etag
) -> properties.get("SomeColumnName").getValueAsString();
private static final Comparator<StudentDto> studentScoreComparator = new Comparator<StudentDto>() {
@Override
public int compare(StudentDto s1, StudentDto s2) {
if (s2.getScore() < s1.getScore()) {
return 1;
}
return s2.getScore() == s1.getScore() ? 0 : 1;
}
};
private static final Comparator<StudentDto> studentScoreComparator = (s1, s2) -> {
if (s2.getScore() < s1.getScore()) {
return 1;
}
return s2.getScore() == s1.getScore() ? 0 : 1;
};