@Implementation
  protected List<UsageStats> queryUsageStats(int intervalType, long beginTime, long endTime) {
    List<UsageStats> results = new ArrayList<>();
    Range<Long> queryRange = Range.closed(beginTime, endTime);
    for (UsageStats stats : usageStatsByIntervalType.get(intervalType)) {
      Range<Long> statsRange = Range.closed(stats.getFirstTimeStamp(), stats.getLastTimeStamp());
      if (queryRange.isConnected(statsRange)) {
        results.add(stats);
      }
    }
    return results;
  }
@Implementation
  protected List<UsageStats> queryUsageStats(int intervalType, long beginTime, long endTime) {
    List<UsageStats> results = new ArrayList<>();
    Range<Long> queryRange = Range.closed(beginTime, endTime);
    for (UsageStats stats : usageStatsByIntervalType.get(intervalType)) {
      Range<Long> statsRange = Range.closed(stats.getFirstTimeStamp(), stats.getLastTimeStamp());
      if (queryRange.isConnected(statsRange)) {
        results.add(stats);
      }
    }
    return results;
  }
@ Implementation protected List < UsageStats > queryUsageStats ( int intervalType , long beginTime , long endTime ) { List < UsageStats > results = new ArrayList <> ( ) ; Range < Long > queryRange = Range . closed ( beginTime , endTime ) ; for ( UsageStats stats : usageStatsByIntervalType . get ( intervalType ) ) { Range < Long > statsRange = Range . closed ( stats . getFirstTimeStamp ( ) , stats . getLastTimeStamp ( ) ) ; if ( queryRange . isConnected ( statsRange ) ) { results . add ( stats ) ; } } return results ; }
Returns aggregated UsageStats added by calling {@link #addUsageStats}.

<p>The real implementation creates these aggregated objects from individual {@link Event}. This
aggregation logic is nontrivial, so the shadow implementation just returns the aggregate data
added using {@link #addUsageStats}.
Returns aggregated UsageStats added by calling { @link #addUsageStats } .