Author: sebb Date: Mon Aug 24 10:50:25 2009 New Revision: 807146 URL: http://svn.apache.org/viewvc?rev=807146&view=rev Log: Genericise StatCalculator
Added: jakarta/jmeter/trunk/src/jorphan/org/apache/jorphan/math/StatCalculatorInteger.java (with props) jakarta/jmeter/trunk/src/jorphan/org/apache/jorphan/math/StatCalculatorLong.java (with props) Modified: jakarta/jmeter/trunk/src/core/org/apache/jmeter/visualizers/SamplingStatCalculator.java jakarta/jmeter/trunk/src/jorphan/org/apache/jorphan/math/StatCalculator.java jakarta/jmeter/trunk/test/src/org/apache/jorphan/math/TestStatCalculator.java Modified: jakarta/jmeter/trunk/src/core/org/apache/jmeter/visualizers/SamplingStatCalculator.java URL: http://svn.apache.org/viewvc/jakarta/jmeter/trunk/src/core/org/apache/jmeter/visualizers/SamplingStatCalculator.java?rev=807146&r1=807145&r2=807146&view=diff ============================================================================== --- jakarta/jmeter/trunk/src/core/org/apache/jmeter/visualizers/SamplingStatCalculator.java (original) +++ jakarta/jmeter/trunk/src/core/org/apache/jmeter/visualizers/SamplingStatCalculator.java Mon Aug 24 10:50:25 2009 @@ -25,7 +25,7 @@ import org.apache.jmeter.samplers.SampleResult; import org.apache.jorphan.logging.LoggingManager; -import org.apache.jorphan.math.StatCalculator; +import org.apache.jorphan.math.StatCalculatorLong; import org.apache.log.Logger; /** @@ -37,7 +37,7 @@ public class SamplingStatCalculator { private static final Logger log = LoggingManager.getLoggerForClass(); - private final StatCalculator calculator = new StatCalculator(); + private final StatCalculatorLong calculator = new StatCalculatorLong(); private final List<Sample> storedValues = new Vector<Sample>(); @@ -312,7 +312,7 @@ return maxThroughput; } - public HashMap getDistribution() { + public HashMap<Number, Number[]> getDistribution() { return calculator.getDistribution(); } Modified: jakarta/jmeter/trunk/src/jorphan/org/apache/jorphan/math/StatCalculator.java URL: http://svn.apache.org/viewvc/jakarta/jmeter/trunk/src/jorphan/org/apache/jorphan/math/StatCalculator.java?rev=807146&r1=807145&r2=807146&view=diff ============================================================================== --- jakarta/jmeter/trunk/src/jorphan/org/apache/jorphan/math/StatCalculator.java (original) +++ jakarta/jmeter/trunk/src/jorphan/org/apache/jorphan/math/StatCalculator.java Mon Aug 24 10:50:25 2009 @@ -25,27 +25,45 @@ import java.util.List; /** - * This class serves as a way to calculate the median of a list of values. It is - * not threadsafe. + * This class serves as a way to calculate the median, max, min etc. of a list of values. + * It is not threadsafe. * - * TODO - currently only works properly for Long (because getDistribution() assumes Long) - * Will never work for mixed values (e.g. Long and Integer) so should probably be converted to - * typed class. */ -public class StatCalculator { - List values = new LinkedList(); +public abstract class StatCalculator<T extends Number & Comparable<T>> { + + private final List<T> values = new LinkedList<T>(); - double sum = 0; + private double sum = 0; - double sumOfSquares = 0; + private double sumOfSquares = 0; - double mean = 0; + private double mean = 0; - double deviation = 0; + private double deviation = 0; - int count = 0; + private int count = 0; - long bytes = 0; + private long bytes = 0; + + private final T ZERO; + + private final T MAX_VALUE; + + private final T MIN_VALUE; + + /** + * This constructor is used to set up particular values for the generic class instance. + * + * @param zero - value to return for Median and PercentPoint if there are no values + * @param min - value to return for minimum if there are no values + * @param max - value to return for maximum if there are no values + */ + public StatCalculator(T zero, T min, T max) { + super(); + ZERO = zero; + MAX_VALUE = max; + MIN_VALUE = min; + } public void clear() { values.clear(); @@ -56,32 +74,13 @@ count = 0; } - public void addValue(long newValue) { - Number val = new Long(newValue); - addValue(val); - } - - public void addValue(int newValue) { - Number val = new Integer(newValue); - addValue(val); - } - - public void addValue(float newValue) { - Number val = new Float(newValue); - addValue(val); - } - - public void addValue(double newValue) { - Number val = new Double(newValue); - addValue(val); - } public void addBytes(long newValue) { bytes += newValue; } - public void addAll(StatCalculator calc) { - Iterator<Number> iter = calc.values.iterator(); + public void addAll(StatCalculator<T> calc) { + Iterator<T> iter = calc.values.iterator(); while (iter.hasNext()) { addValue(iter.next()); } @@ -89,9 +88,9 @@ public Number getMedian() { if (count > 0) { - return (Number) values.get((int) (values.size() * .5)); + return values.get((int) (values.size() * .5)); } - return new Long(0); + return ZERO; } public long getTotalBytes() { @@ -107,11 +106,11 @@ * @param percent * @return number of values less than the percentage */ - public Number getPercentPoint(float percent) { + public T getPercentPoint(float percent) { if (count > 0) { - return (Number) values.get((int) (values.size() * percent)); + return values.get((int) (values.size() * percent)); } - return new Long(0); + return ZERO; } /** @@ -123,25 +122,30 @@ * @param percent * @return number of values less than the percentage */ - public Number getPercentPoint(double percent) { + public T getPercentPoint(double percent) { if (count > 0) { - return (Number) values.get((int) (values.size() * percent)); + return values.get((int) (values.size() * percent)); } - return new Long(0); + return ZERO; } /** - * The method has a limit of 1% as the finest granularity. We do this to - * make sure we get a whole number for iterating. + * Returns the distribution of the values in the list. + * + * TODO round values to reduce the number of distinct entries. * + * @return map containing either Integer or Long keys; entries are a Number array containing the key and the [Integer] count. + * TODO - why is the key value also stored in the entry array? */ - public synchronized HashMap getDistribution() { - HashMap<Long, Number[]> items = new HashMap<Long, Number[]>(); - Iterator<Number> itr = this.values.iterator(); + public synchronized HashMap<Number, Number[]> getDistribution() { + HashMap<Number, Number[]> items = new HashMap<Number, Number[]>(); + Iterator<T> itr = this.values.iterator(); Number[] dis; while (itr.hasNext()) { - Number num = itr.next(); - Long nx = new Long(itr.next().longValue()); // TODO this assumes the entries are all Long + Number nx = itr.next(); + if (!(nx instanceof Integer || nx instanceof Long)){ + nx=new Long(nx.longValue()); // convert to Long unless Integer or Long + } if (items.containsKey(nx)) { dis = items.get(nx); dis[1] = new Integer(dis[1].intValue() + 1); @@ -164,25 +168,25 @@ return deviation; } - public Number getMin() { + public T getMin() { if (count > 0) { - return (Number) values.get(0); + return values.get(0); } - return new Long(Long.MIN_VALUE); + return MIN_VALUE; } - public Number getMax() { + public T getMax() { if (count > 0) { - return (Number) values.get(count - 1); + return values.get(count - 1); } - return new Long(Long.MAX_VALUE); + return MAX_VALUE; } public int getCount() { return count; } - public void addValue(Number val) { + public void addValue(T val) { addSortedValue(val); count++; double currentVal = val.doubleValue(); @@ -192,10 +196,7 @@ deviation = Math.sqrt((sumOfSquares / count) - (mean * mean)); } - /** - * @param val - */ - private void addSortedValue(Number val) { + private void addSortedValue(T val) { int index = Collections.binarySearch(values, val); if (index >= 0 && index < values.size()) { values.add(index, val); Added: jakarta/jmeter/trunk/src/jorphan/org/apache/jorphan/math/StatCalculatorInteger.java URL: http://svn.apache.org/viewvc/jakarta/jmeter/trunk/src/jorphan/org/apache/jorphan/math/StatCalculatorInteger.java?rev=807146&view=auto ============================================================================== --- jakarta/jmeter/trunk/src/jorphan/org/apache/jorphan/math/StatCalculatorInteger.java (added) +++ jakarta/jmeter/trunk/src/jorphan/org/apache/jorphan/math/StatCalculatorInteger.java Mon Aug 24 10:50:25 2009 @@ -0,0 +1,33 @@ +/* + * Licensed to the Apache Software Foundation (ASF) under one or more + * contributor license agreements. See the NOTICE file distributed with + * this work for additional information regarding copyright ownership. + * The ASF licenses this file to You under the Apache License, Version 2.0 + * (the "License"); you may not use this file except in compliance with + * the License. You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + * + */ + +package org.apache.jorphan.math; + +/** + * StatCalculator for Integer values + */ +public class StatCalculatorInteger extends StatCalculator<Integer> { + + public StatCalculatorInteger() { + super(new Integer(0), new Integer(Integer.MIN_VALUE), new Integer(Integer.MAX_VALUE)); + } + + public void addValue(int val){ + super.addValue(new Integer(val)); + } +} Propchange: jakarta/jmeter/trunk/src/jorphan/org/apache/jorphan/math/StatCalculatorInteger.java ------------------------------------------------------------------------------ svn:eol-style = native Propchange: jakarta/jmeter/trunk/src/jorphan/org/apache/jorphan/math/StatCalculatorInteger.java ------------------------------------------------------------------------------ svn:keywords = Author Date Id Revision Added: jakarta/jmeter/trunk/src/jorphan/org/apache/jorphan/math/StatCalculatorLong.java URL: http://svn.apache.org/viewvc/jakarta/jmeter/trunk/src/jorphan/org/apache/jorphan/math/StatCalculatorLong.java?rev=807146&view=auto ============================================================================== --- jakarta/jmeter/trunk/src/jorphan/org/apache/jorphan/math/StatCalculatorLong.java (added) +++ jakarta/jmeter/trunk/src/jorphan/org/apache/jorphan/math/StatCalculatorLong.java Mon Aug 24 10:50:25 2009 @@ -0,0 +1,33 @@ +/* + * Licensed to the Apache Software Foundation (ASF) under one or more + * contributor license agreements. See the NOTICE file distributed with + * this work for additional information regarding copyright ownership. + * The ASF licenses this file to You under the Apache License, Version 2.0 + * (the "License"); you may not use this file except in compliance with + * the License. You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + * + */ + +package org.apache.jorphan.math; + +/** + * StatCalculator for Long values + */ +public class StatCalculatorLong extends StatCalculator<Long> { + + public StatCalculatorLong() { + super(new Long(0L), new Long(Long.MIN_VALUE), new Long(Long.MAX_VALUE)); + } + + public void addValue(long val){ + super.addValue(new Long(val)); + } +} Propchange: jakarta/jmeter/trunk/src/jorphan/org/apache/jorphan/math/StatCalculatorLong.java ------------------------------------------------------------------------------ svn:eol-style = native Propchange: jakarta/jmeter/trunk/src/jorphan/org/apache/jorphan/math/StatCalculatorLong.java ------------------------------------------------------------------------------ svn:keywords = Author Date Id Revision Modified: jakarta/jmeter/trunk/test/src/org/apache/jorphan/math/TestStatCalculator.java URL: http://svn.apache.org/viewvc/jakarta/jmeter/trunk/test/src/org/apache/jorphan/math/TestStatCalculator.java?rev=807146&r1=807145&r2=807146&view=diff ============================================================================== --- jakarta/jmeter/trunk/test/src/org/apache/jorphan/math/TestStatCalculator.java (original) +++ jakarta/jmeter/trunk/test/src/org/apache/jorphan/math/TestStatCalculator.java Mon Aug 24 10:50:25 2009 @@ -18,11 +18,13 @@ package org.apache.jorphan.math; +import java.util.Map; + import junit.framework.TestCase; public class TestStatCalculator extends TestCase { - StatCalculator calc; + private StatCalculatorLong calc; /** * @@ -40,7 +42,7 @@ @Override public void setUp() { - calc = new StatCalculator(); + calc = new StatCalculatorLong(); } public void testPercentagePoint() throws Exception { @@ -77,15 +79,25 @@ public void testLong(){ calc.addValue(0L); calc.addValue(2L); - assertEquals(Long.valueOf(2),calc.getMax()); - assertEquals(Long.valueOf(0),calc.getMin()); - calc.getDistribution(); + calc.addValue(2L); + final Long long0 = Long.valueOf(0); + final Long long2 = Long.valueOf(2); + assertEquals(long2,calc.getMax()); + assertEquals(long0,calc.getMin()); + Map<Number, Number[]> map = calc.getDistribution(); + assertTrue(map.containsKey(long0)); + assertTrue(map.containsKey(long2)); } + public void testInteger(){ - calc.addValue(0); - calc.addValue(2); - assertEquals(Integer.valueOf(2),calc.getMax()); - assertEquals(Integer.valueOf(0),calc.getMin()); -// calc.getDistribution(); // currently fails with ClassCastException + StatCalculatorInteger calci = new StatCalculatorInteger(); + calci.addValue(0); + calci.addValue(2); + calci.addValue(2); + assertEquals(Integer.valueOf(2),calci.getMax()); + assertEquals(Integer.valueOf(0),calci.getMin()); + Map<Number, Number[]> map = calci.getDistribution(); + assertTrue(map.containsKey(Integer.valueOf(0))); + assertTrue(map.containsKey(Integer.valueOf(2))); } } --------------------------------------------------------------------- To unsubscribe, e-mail: jmeter-dev-unsubscr...@jakarta.apache.org For additional commands, e-mail: jmeter-dev-h...@jakarta.apache.org