在将老式的用法转换为Optional.ifPresent
时,我遇到了问题。这是该代码的先前版本。
State state = State.OK;
final Optional<Person> checkExistingPerson = checkIt();
if(checkExistingPerson.isPresent()) {
Person person = checkExistingPerson.get();
if("blah".equals(person.getName())) {
state = State.DUPLICATE;
} else {
state = State.RESTORED;
}
return Member(person.getId(), state);
}
return Member(null, state);
这是Optional.ifPresent
的用法
State state = State.OK;
final Optional<Person> checkExistingPerson = checkIt();
checkExistingPerson.ifPresent(person -> {
if("blah".equals(person.getName())) {
state = State.DUPLICATE;
} else {
state = State.NEW;
}
return Member(person.getId(), state);
});
return Member(null, state);
针对我的问题,使用Optional
的最佳方法是什么?谢谢!
答案 0 :(得分:3)
final
。ifPresent
接受Consumer
,因此它没有返回值,因此您不能使用return Member(person.getId(), state);
(还要记住,您在lambda中,所以return
是不会退出您的方法,而是退出lambda)。 map
接受具有返回值的Function
,因此您可以使用它代替ifPresent
。
通过在lambda内移动state
并使用map
和orElseGet
,这是重构代码的方式:
return checkExistingPerson.map(person -> {
State state;
if("blah".equals(person.getName())) {
state = State.DUPLICATE;
} else {
state = State.NEW;
}
return Member(person.getId(), state);
})
.orElseGet(() -> Member(null, State.OK));
答案 1 :(得分:3)
您不能在lambda表达式中更改局部变量的值。此外,ifPresent
无法返回值,因为其返回类型为void
。
相反,您应该使用Optional.map
,它可以对Optional
包裹的对象进行转换:
return checkExistingPerson
.map(person -> new Member(
person.getId(),
"blah".equals(person.getName()) ? State.DUPLICATE : State.RESTORED))
.orElse(new Member(null, State.OK));
答案 2 :(得分:1)
如果要访问lambda表达式内的局部变量,则变量应为final或有效地为final,这意味着它们不能被修改here,也可以在lambda表达式内声明变量。 {1}}将使用ifPresent
作为没有返回类型的参数,您使用Consumer
将会使用map
和根据@Loris的参数
答案 3 :(得分:1)
在内部方法中,如果未将外部变量定义为final,则不能引用它们,您可以像这样更改您的方法:
COUNT(DISTINCT user_id)