2016-08-07 10 views
2
class Stock{ 
    double profit; 
    double profitPercentage; 
    public double getProfit(){ 
     return profit; 
    } 
    public double getProfitPercentage(){ 
     return profitPercentage; 
    } 
} 
List<Stock> stocks = getAllStocks(); 
stocks.stream.collect(Collectors.summarizingDouble(Stock:getProfit)).getSum(); 
stocks.stream.collect(Collectors.summarizingDouble(Stock:getProfitPercentage)).getSum(); 

ストリームのシングルパスで行う方法がわかりませんでした。どんな助けやポインタも良いでしょう。Javaのストリームから2つの合計を集める方法

+1

あなたは[このような](http://stackoverflow.com/a/30211021/1743880)を探しています。 – Tunaki

+0

リンクはgroupbyとsumのようなものを示していました。私にとっては、2つのフィールドとグループの合計を実行する必要があります。 –

+0

すべての利益と利益のパーセンテージの合計はありますか? –

答えて

1

簡単な方法は、カスタムコレクタークラスを作成することです。

public class StockStatistics { 

    private DoubleSummaryStatistics profitStat = new DoubleSummaryStatistics(); 
    private DoubleSummaryStatistics profitPercentageStat = new DoubleSummaryStatistics(); 

    public void accept(Stock stock) { 
     profitStat.accept(stock.getProfit()); 
     profitPercentageStat.accept(stock.getProfitPercentage()); 
    } 

    public StockStatistics combine(StockStatistics other) { 
     profitStat.combine(other.profitStat); 
     profitPercentageStat.combine(other.profitPercentageStat); 
     return this; 
    } 

    public static Collector<Stock, ?, StockStatistics> collector() { 
     return Collector.of(StockStatistics::new, StockStatistics::accept, StockStatistics::combine); 
    } 

    public DoubleSummaryStatistics getProfitStat() { 
     return profitStat; 
    } 

    public DoubleSummaryStatistics getProfitPercentageStat() { 
     return profitPercentageStat; 
    } 

} 

このクラスは、2つのラッパーとして機能しますDoubleSummaryStatistics。それは要素が受け入れられるたびにそれらに委譲します。あなたの場合は、合計にのみ関心があるので、DoubleSummaryStatisticsの代わりにCollectors.summingDoubleを使用することもできます。また、getProfitStatgetProfitPercentageStatという2つの統計を返します。あるいは、両方の合計のみを含むdouble[]を返すフィニッシャ操作を追加することもできます。

その後、あなたはより多くの一般的な方法は、他のコレクターをペアリングできるコレクタを作成することです

StockStatistics stats = stocks.stream().collect(StockStatistics.collector()); 
System.out.println(stats.getProfitStat().getSum()); 
System.out.println(stats.getProfitPercentageStat().getSum()); 

を使用することができます。 pairingコレクターはin this answerと書かれており、in the StreamEx libraryも使用できます。

double[] sums = stocks.stream().collect(MoreCollectors.pairing(
    Collectors.summingDouble(Stock::getProfit), 
    Collectors.summingDouble(Stock::getProfitPercentage), 
    (sum1, sum2) -> new double[] { sum1, sum2 } 
)); 

利益の合計はsums[0]になり、利益率の合計はsums[1]になります。このスニペットでは、合計のみが保持され、統計値全体は保持されません。

関連する問題