Java 8 Optional和flatMap - 有什么问题?

4

一些代码:

public class Player {
    Team team;
    String name;
}

public class Team {
    List<Player> players;
}

public class Demo {

    @Inject
    TeamDAO teamDAO;

    @Inject
    PlayerDAO playerDAO;

    List<String> findTeamMatesNames(String playerName) {
        Optional<Player> player = Optional.ofNullable(playerDAO.get(playerName));

        return player.flatMap(p -> teamDAO.findPlayers(p.team))
            .map(p -> p.name)
            .orElse(Collections.emptyList());
    }
}

为什么我做不到这个呢?在flatMap方法中,我得到了一个错误:“类型不匹配:无法将List转换为Optional”。

我的目标是:

  1. 如果optional对象存在,我想根据此optional对象属性获取项目列表

  2. 如果optional对象不存在,我想返回空列表


你得到了什么错误? - talex
你遇到了什么错误?teamDAO.finPlayers是什么意思? - user2504380
findTeamMatesNames 中的 team 是从哪里来的? - Dante WWWW
你所问的并不是重点。在flatMap中,我得到了以下错误信息:“类型不匹配:无法将List<Player>转换为Optional<Object>”。 - Dariusz Mydlarz
看起来你混淆了流和可选API。Optional中的flatMap()用于解包嵌套的Optionals,但是你的lambda返回的是一个Player列表,而不是Optional<Player>。 - Dirk Lachowski
显示剩余3条评论
1个回答

10

您可以使用map执行所需操作。如果Optional为空,则不会发生map操作,但会再次留下一个空的Optional。您可以在之后提供备用值:

player.map(p -> teamDAO.findPlayers(p.team)).orElse(Collections.emptyList())

List中的Player对象映射为String类型的List,无法使用Optional实现;这是一个Stream任务:

Optional<Player> player = Optional.ofNullable(playerDAO.get(playerName));
return player.map(p -> teamDAO.findPlayers(p.team)
                           .stream().map(tp -> tp.name).collect(Collectors.toList()))
             .orElse(Collections.emptyList());

我没有意识到我必须在第一个map函数内执行下一个操作。谢谢! - Dariusz Mydlarz
1
@dmydlarz:事后也可以做到,例如player.map(p -> teamDAO.findPlayers(p.team)).orElse(Collections.emptyList()) .stream().map(tp -> tp.name).collect(Collectors.toList())具有相同的语义,但在Optional为空的情况下会对空流执行不必要的收集操作。 - Holger

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接