Assuming your TimePeriodCalc class has all the necessary getters, it should get the list you want:
List<TimePeriodCalc> result = new ArrayList<>( list.stream() .collect(Collectors.groupingBy(TimePeriodCalc::getAtDate, Collectors.collectingAndThen(Collectors.toList(), TimePeriodCalc::avgTimePeriodCalc))) .values() );
Where TimePeriodCalc.avgTimePeriodCalc is this method in the TimePeriodCalc class:
public static TimePeriodCalc avgTimePeriodCalc(List<TimePeriodCalc> list){ return new TimePeriodCalc( list.stream().collect(Collectors.averagingDouble(TimePeriodCalc::getOccupancy)), list.stream().collect(Collectors.averagingDouble(TimePeriodCalc::getEfficiency)), list.get(0).getAtDate() ); }
The above can be combined into this monster:
List<TimePeriodCalc> result = new ArrayList<>( list.stream() .collect(Collectors.groupingBy(TimePeriodCalc::getAtDate, Collectors.collectingAndThen( Collectors.toList(), a -> { return new TimePeriodCalc( a.stream().collect(Collectors.averagingDouble(TimePeriodCalc::getOccupancy)), a.stream().collect(Collectors.averagingDouble(TimePeriodCalc::getEfficiency)), a.get(0).getAtDate() ); } ))) .values());
When entering:
List<TimePeriodCalc> list = new ArrayList<>(); list.add(new TimePeriodCalc(10,10,"a")); list.add(new TimePeriodCalc(10,10,"b")); list.add(new TimePeriodCalc(10,10,"c")); list.add(new TimePeriodCalc(5,5,"a")); list.add(new TimePeriodCalc(0,0,"b"));
This will give:
TimePeriodCalc [occupancy=7.5, efficiency=7.5, atDate=a] TimePeriodCalc [occupancy=5.0, efficiency=5.0, atDate=b] TimePeriodCalc [occupancy=10.0, efficiency=10.0, atDate=c]