I can do it with a for loop. But I have not yet been able to do it with streams.
Let’s simplify your problem by defining a record with only two member fields.
record Amount( LocalDate date , BigDecimal revenue ) { }
Make some example data. We have two BigDecimal values for each of two LocalDate keys. January 23rd has 7 and 42, while April 1 has 1.2 and 1.1.
List < Amount > amounts =
List.of(
new Amount( LocalDate.of( 2022 , Month.JANUARY , 23 ) , new BigDecimal( "7" ) ) ,
new Amount( LocalDate.of( 2022 , Month.APRIL , 1 ) , new BigDecimal( "1.2" ) ) ,
new Amount( LocalDate.of( 2022 , Month.APRIL , 1 ) , new BigDecimal( "1.1" ) ) ,
new Amount( LocalDate.of( 2022 , Month.JANUARY , 23 ) , new BigDecimal( "42" ) )
);
Loop those.
NavigableMap < LocalDate, BigDecimal > mapTotalByDate = new TreeMap <>();
for ( Amount amount : amounts )
{
if ( mapTotalByDate.get( amount.date() ) == null )
{
mapTotalByDate.put( amount.date , amount.revenue );
} else
{
mapTotalByDate.put( amount.date , mapTotalByDate.get( amount.date ).add( amount.revenue ) );
}
}
mapTotalByDate = {2022-01-23=49, 2022-04-01=2.3}
Or change that for loop to use switch rather than cascading if, as suggested by IntelliJ. I prefer this as it seems easier to read.
for ( Amount amount : amounts )
{
switch ( mapTotalByDate.get( amount.date() ) )
{
case null -> mapTotalByDate.put( amount.date , amount.revenue );
default -> mapTotalByDate.put( amount.date , mapTotalByDate.get( amount.date ).add( amount.revenue ) );
}
}
Eliminate one of lookup on the map.
for ( Amount amount : amounts )
{
BigDecimal subtotal = mapTotalByDate.get( amount.date() );
switch ( subtotal )
{
case null -> mapTotalByDate.put( amount.date , amount.revenue );
default -> mapTotalByDate.put( amount.date , subtotal.add( amount.revenue ) );
}
}