使用Java8 Streams时是否可以获取ArrayList <object>的索引?

时间:2017-03-14 14:30:33

标签: java arraylist lambda java-8 java-stream

我是Java 8 lambda和stream的新手。对于练习,我试图在可能的情况下将一些方法从学校项目“翻译”为lambdas / streams。 这是旧方法。

正如你所看到的,我需要给丢弃方法一个int,这是玩家手中第一张可玩牌的编号。

public Card autoPlay(Card flipped) {
    for (int i = 0; i < super.getHand().size(); i++) {
        if (super.getHand().get(i).isCompatible(flipped)) { //check if card from hand is compatible with flipped card (same number or color)
            return (this.discard(i)); //remove from hand and returns it
        }
    }
    return null; //if any compatible card found
}

到目前为止,我的方法的新版本是:

public Card newAutoPlay(Card flipped){
   return super.getHand().stream().filter(card -> card.isCompatible(flipped)).findFirst().get();

}

我发现了如何获得第一个兼容的卡,但不知道如何获取它的索引...我读了关于IntStreams(并使用列表的大小作为范围),但我不明白如何使用在这种特殊情况下。

是否有可能实现我想要做的事情,或者这样做不是一个好主意?

编辑:在探索了这个问题后,在这种情况下使用流带来了太多的复杂性,并且没有足够的可读性来解决这个简单的问题。所以我选择了for循环。还有其他一些变化,但核心思想保持不变。谢谢大家的帮助。

@Override
public String play(Uno unoGame) {
    int i = 0;
    boolean found = false;

    for (i = 0; i < super.getHand().size() && !found; i++) {
        found = super.getHand().get(i).isCompatible(unoGame.getFlippedCard());
    }

    return found ? "play " + i : "draw";
}

2 个答案:

答案 0 :(得分:3)

我建议使用Java 8 lambdas对现有代码进行以下解决方案,这需要将discard(int index)的签名更改为discard(Card card),假设Card确实实现了equals(Object obj)hashCode()

public Card autoPlay(Card flipped) {
    Optional<Card> card = getHand().stream()
            .filter(flipped::isCompatible)
            .findFirst();
    card.ifPresent(this::discard);
    return card.orElse(null);
}

private void discard(Card card) {
    // your code removing the first matching card from your hand
}

您可以考虑将null的签名更改为Card autoPlay(Card flipped),而不是返回Optional<Card> autoPlay(Card flipped)

答案 1 :(得分:1)

一个班轮:

   IntStream.range(0,getHand()::size).filter(i -> super.getHand().get(i).isCompatible(flipped))
                .mapToObj(Integer::new).findFirst().map(this::discard).orElse(null);

有必要mapToObj,因为map类型Optional上的int函数不存在。可悲的是,java缺乏原生支持对,这会使这不那么难看。他们可以“用索引流”。但请记住:Streams意味着无限,因此没有索引。