2017-11-04 8 views
1

は、私は、次の構文があるとしましょう:私は私の最初の反復からのリストを持っているList<Athlete> athleteListのJava 8は、フィルタオプションを使用して、ネストされたリストに和演算を実行する

は今、私は新しい選手を作成してここに集まっ

public class Athlete { 
    private String  name; 
    private int   someIdentifier; 
    private Double  height; 
    private Double  weight; 
    private List<Shoes> shoes; 
    // getters 
    // setters 
    public class Shoes { 
     private String name; 
     private boolean ball; 
     private int  someNumber; 
     private int  someOtherNumber; 
     // getters 
     // setters 
    } 
} 

をオブジェクトがあり、それらがすでにリストに存在するかどうかを確認したい場合は、それらのフィールドにいくつかのフィールドを追加したいと考えています。 (...)メソッド私mergeAthletesに()

athleteList.stream() 
        .filter(at -> filterAthlete(at, newAthlete)) 
        .map(at -> mergeAthletes(at, newAthlete)) 
        .collect(Collectors.toList()); 

private boolean filterAthlete(Athlete firstAthlete, Athlete secondAthlete) { 
     if (firstAthlete.getName().equals(secondAthlete.getName()) 
       && firstAthlete.getSomeIdentifier() == secondAthlete.getSomeIdentifier()) { 
      return true; 
     } else { 
      return false; 
     } 
    } 

private Athlete mergeAthletes(Athlete firstAthlete, Athlete secondAthlete) { 

     for (Shoes firstShoe : firstAthlete.getShoes()) { 
      for (Shoes secondShoe : secondAthlete.getShoes()) { 
       if (firstShoe.getBrand().equals(secondShoe.getBrand()) && firstShoe.getColor().equals(secondShoe.getColor())) { 
        firstShoe.setSomeNumber(firstShoe.getSomeNumber() + secondShoe.getSomeNumber()); 
        firstShoe.setSomeOtherNumber(firstShoe.getSomeOtherNumber() + secondShoe.getSomeOtherNumber()); 
       } 
      } 
     } 

     return firstAthlete; 
    } 

しかし、私は、ストリームを使用するための方法を見つけるしたいと思います:

私は正常に動作し、以下を試してみました。二重に加えての代わりに、私の場合、条件の代わりに機能を使用してBiConsumer、私mergeAthletes法で

BiConsumer<Shoes, Shoes> reducer = (shoe1, shoe2) -> { 
      shoe1.setSomeNumber(shoe1.getSomeNumber() + shoe2.getSomeNumber()); 
      shoe1.setSomeOtherNumber(shoe1.getSomeOtherNumber() + shoe2.getSomeOtherNumber()); 
     }; 

     Function<Shoes, List<Object>> compositeKey = shoes -> Arrays.<Object> asList(shoes.getBrand(), 
       shoes.getColor()); 

は、私はそのようなことをやって考えますそれぞれのループのために、私はそれを行う方法を考え出していない。

ご協力いただければ幸いです。あなたの靴は不変(なしset...方法)なかった場合

+0

きっとマップにあなたの 'Athlete'sを置くことは、より効率的でしょうか? –

+0

@JoeCかもしれませんが、それは私のデータベーススキーマの変更を意味します。それで、これがそうであると言われる方法です。 –

答えて

2
firstAthlete.getShoes().forEach(shoe1 -> 
    secondAthlete.getShoes().stream().filter(shoe2 -> 
     shoe1.getBrand().equals(shoe2.getBrand()) && shoe1.getColor().equals(shoe2.getColor())) 
    ).forEach(shoe2 -> { 
     shoe1.setSomeNumber(shoe1.getSomeNumber() + shoe2.getSomeNumber()); 
     shoe1.setSomeOtherNumber(shoe1.getSomeOtherNumber() + shoe2.getSomeOtherNumber()); 
    }) 

あなたはあなたの要件に応じて、第二forEach、代わりに最初のものの、おそらくmapの代わりにreduceを使用したい

(また、firstAthlete.getName() == secondAthlete.getName()は非常に可能性の高いエラーであり、あなたが靴を比較するときのようにそこにequalsをしたい。)

+0

ありがとうございます。うん、私はダミーオブジェクトを書いていたので、文字列の比較は私の間違いでした。 2番目のforEachでは、それぞれshoe1ではなくfirstShoeを意味しますが、shoe2ではなくsecondShoeを意味します。私はそれを変更し、期待どおりに動作します。再度、感謝します! –

+0

はい、修正されました。コピー・ペースト・エラーだけです。 –

関連する問題