private void calcMinMaxAvg(List<MeasurementDataNumericHighLowComposite> metricData) { int averageCount = 0; for (MeasurementDataNumericHighLowComposite measurement : metricData) { if (!Double.isNaN(measurement.getLowValue())) { min = Math.min(min, measurement.getLowValue()); } if (!Double.isNaN(measurement.getHighValue())) { max = Math.max(max, measurement.getHighValue()); } if (!Double.isNaN(measurement.getValue())) { average = average + measurement.getValue(); averageCount++; } } average = average / averageCount; }
/** * When the scale is adjusted down to a level where bars no longer have highs and lows different * from the avg value then have probably hit a scale where aggregates no longer exist and we are * looking the individual values. At the very least the data is less interesting and a trendline * connecting the points has less meaning because we are essentially a scatterplot. A different * algorithm could be used here but this will suffice. * * @return true if the graphs should show the bar avg line meaning there is aggregates in the data * @see StackedBarMetricGraphImpl */ public boolean showBarAvgTrendLine() { int numberOfAggBars = 0; for (MeasurementDataNumericHighLowComposite measurement : metricData) { boolean noValuesInCurrentBarUndefined = (!Double.isNaN(measurement.getValue()) && !Double.isNaN(measurement.getHighValue()) && !Double.isNaN(measurement.getLowValue())); boolean foundAggregateBar = (measurement.getValue() != measurement.getHighValue() || measurement.getHighValue() != measurement.getLowValue()); // if there exists a even one aggregate bar then I can short circuit this and exit if (noValuesInCurrentBarUndefined && foundAggregateBar) { numberOfAggBars++; if (numberOfAggBars > 4) { return true; } } } return false; }
@Override /** * Format the json for the front JSNI(javascript) UI to consume. * * @todo: future: this should really use GSON or some Json marshaller */ public String getJsonMetrics() { StringBuilder sb = new StringBuilder(); if (null != metricData) { sb = new StringBuilder("["); long firstBarTime = metricData.get(0).getTimestamp(); long secondBarTime = metricData.get(1).getTimestamp(); long barDuration = secondBarTime - firstBarTime; String barDurationString = MeasurementConverterClient.format( (double) barDuration, MeasurementUnits.MILLISECONDS, true); calculateOOB(); // find the lowest value and use it's UOM to translated everything else into MeasurementDataNumericHighLowComposite lowestValue = null; for (MeasurementDataNumericHighLowComposite measurement : metricData) { if (!Double.isNaN(measurement.getValue())) { if (null == lowestValue) { lowestValue = measurement; } if (measurement.getLowValue() < lowestValue.getLowValue()) { lowestValue = measurement; } } } MeasurementNumericValueAndUnits adjustedMeasurementUnitsAndValue = MeasurementConverterClient.fit(lowestValue.getLowValue(), definition.getUnits()); adjustedMeasurementUnits = adjustedMeasurementUnitsAndValue.getUnits(); for (MeasurementDataNumericHighLowComposite measurement : metricData) { sb.append("{ \"x\":" + measurement.getTimestamp() + ","); if (null != lastOOB) { sb.append(" \"baselineMin\":" + lastOOB.getBlMin() + ", "); sb.append(" \"baselineMax\":" + lastOOB.getBlMax() + ", "); } if (!Double.isNaN(measurement.getValue())) { Double newHigh = normalizeUnitsAndValues( new MeasurementNumericValueAndUnits( measurement.getHighValue(), definition.getUnits()), adjustedMeasurementUnits); Double newAvg = normalizeUnitsAndValues( new MeasurementNumericValueAndUnits( measurement.getValue(), definition.getUnits()), adjustedMeasurementUnits); Double newLow = normalizeUnitsAndValues( new MeasurementNumericValueAndUnits( measurement.getLowValue(), definition.getUnits()), adjustedMeasurementUnits); sb.append(" \"barDuration\": \"" + barDurationString + "\", "); sb.append(" \"high\":" + newHigh + ","); sb.append( " \"highFormatted\":\"" + MeasurementConverterClient.format( measurement.getHighValue(), definition.getUnits(), true, 0, 3) + "\","); sb.append(" \"low\":" + cleanseLow(newLow, newAvg, newHigh) + ","); sb.append( " \"lowFormatted\":\"" + MeasurementConverterClient.format( cleanseLow( measurement.getLowValue(), measurement.getValue(), measurement.getHighValue()), definition.getUnits(), true, 0, 3) + "\","); sb.append(" \"avg\":" + newAvg + ","); sb.append( " \"avgFormatted\":\"" + MeasurementConverterClient.format( measurement.getValue(), definition.getUnits(), true, 0, 3) + "\"},"); } else { // give it some values so that we dont have NaN sb.append(" \"high\":0,"); sb.append(" \"low\":0,"); sb.append(" \"avg\":0,"); sb.append(" \"nodata\":true },"); } if (!sb.toString().endsWith("},")) { sb.append(" },"); } } sb.setLength(sb.length() - 1); // delete the last ',' sb.append("]"); } Log.debug("Json data for: " + getChartTitle()); Log.debug(sb.toString()); return sb.toString(); }