001package stdlib; 002 003/* *********************************************************************** 004 * Compilation: javac StdStats.java 005 * Execution: java StdStats < input.txt 006 * 007 * Library of statistical functions. 008 * 009 * The test client reads an array of real numbers from standard 010 * input, and computes the minimum, mean, maximum, and 011 * standard deviation. 012 * 013 * The functions all throw a NullPointerException if the array 014 * passed in is null. 015 016 * % more tiny.txt 017 * 5 018 * 3.0 1.0 2.0 5.0 4.0 019 * 020 * % java StdStats < tiny.txt 021 * min 1.000 022 * mean 3.000 023 * max 5.000 024 * std dev 1.581 025 * 026 *************************************************************************/ 027 028/** 029 * <i>Standard statistics</i>. This class provides methods for computing 030 * statistics such as min, max, mean, sample standard deviation, and 031 * sample variance. 032 * <p> 033 * For additional documentation, see 034 * <a href="http://introcs.cs.princeton.edu/22library">Section 2.2</a> of 035 * <i>Introduction to Programming in Java: An Interdisciplinary Approach</i> 036 * by Robert Sedgewick and Kevin Wayne. 037 */ 038public final class StdStats { 039 040 private StdStats() { } 041 042 /** 043 * Return maximum value in array, -infinity if no such value. 044 */ 045 public static double max(double[] a) { 046 double max = Double.NEGATIVE_INFINITY; 047 for (int i = 0; i < a.length; i++) { 048 if (a[i] > max) max = a[i]; 049 } 050 return max; 051 } 052 053 /** 054 * Return maximum value in subarray a[lo..hi], -infinity if no such value. 055 */ 056 public static double max(double[] a, int lo, int hi) { 057 if (lo < 0 || hi >= a.length || lo > hi) 058 throw new RuntimeException("Subarray indices out of bounds"); 059 double max = Double.NEGATIVE_INFINITY; 060 for (int i = lo; i <= hi; i++) { 061 if (a[i] > max) max = a[i]; 062 } 063 return max; 064 } 065 066 /** 067 * Return maximum value of array, Integer.MIN_VALUE if no such value 068 */ 069 public static int max(int[] a) { 070 int max = Integer.MIN_VALUE; 071 for (int i = 0; i < a.length; i++) { 072 if (a[i] > max) max = a[i]; 073 } 074 return max; 075 } 076 077 /** 078 * Return minimum value in array, +infinity if no such value. 079 */ 080 public static double min(double[] a) { 081 double min = Double.POSITIVE_INFINITY; 082 for (int i = 0; i < a.length; i++) { 083 if (a[i] < min) min = a[i]; 084 } 085 return min; 086 } 087 088 /** 089 * Return minimum value in subarray a[lo..hi], +infinity if no such value. 090 */ 091 public static double min(double[] a, int lo, int hi) { 092 if (lo < 0 || hi >= a.length || lo > hi) 093 throw new RuntimeException("Subarray indices out of bounds"); 094 double min = Double.POSITIVE_INFINITY; 095 for (int i = lo; i <= hi; i++) { 096 if (a[i] < min) min = a[i]; 097 } 098 return min; 099 } 100 101 /** 102 * Return minimum value of array, Integer.MAX_VALUE if no such value 103 */ 104 public static int min(int[] a) { 105 int min = Integer.MAX_VALUE; 106 for (int i = 0; i < a.length; i++) { 107 if (a[i] < min) min = a[i]; 108 } 109 return min; 110 } 111 112 /** 113 * Return average value in array, NaN if no such value. 114 */ 115 public static double mean(double[] a) { 116 if (a.length == 0) return Double.NaN; 117 double sum = sum(a); 118 return sum / a.length; 119 } 120 121 /** 122 * Return average value in subarray a[lo..hi], NaN if no such value. 123 */ 124 public static double mean(double[] a, int lo, int hi) { 125 int length = hi - lo + 1; 126 if (lo < 0 || hi >= a.length || lo > hi) 127 throw new RuntimeException("Subarray indices out of bounds"); 128 if (length == 0) return Double.NaN; 129 double sum = sum(a, lo, hi); 130 return sum / length; 131 } 132 133 /** 134 * Return average value in array, NaN if no such value. 135 */ 136 public static double mean(int[] a) { 137 if (a.length == 0) return Double.NaN; 138 double sum = 0.0; 139 for (int i = 0; i < a.length; i++) { 140 sum = sum + a[i]; 141 } 142 return sum / a.length; 143 } 144 145 /** 146 * Return sample variance of array, NaN if no such value. 147 */ 148 public static double var(double[] a) { 149 if (a.length == 0) return Double.NaN; 150 double avg = mean(a); 151 double sum = 0.0; 152 for (int i = 0; i < a.length; i++) { 153 sum += (a[i] - avg) * (a[i] - avg); 154 } 155 return sum / (a.length - 1); 156 } 157 158 /** 159 * Return sample variance of subarray a[lo..hi], NaN if no such value. 160 */ 161 public static double var(double[] a, int lo, int hi) { 162 int length = hi - lo + 1; 163 if (lo < 0 || hi >= a.length || lo > hi) 164 throw new RuntimeException("Subarray indices out of bounds"); 165 if (length == 0) return Double.NaN; 166 double avg = mean(a, lo, hi); 167 double sum = 0.0; 168 for (int i = lo; i <= hi; i++) { 169 sum += (a[i] - avg) * (a[i] - avg); 170 } 171 return sum / (length - 1); 172 } 173 174 /** 175 * Return sample variance of array, NaN if no such value. 176 */ 177 public static double var(int[] a) { 178 if (a.length == 0) return Double.NaN; 179 double avg = mean(a); 180 double sum = 0.0; 181 for (int i = 0; i < a.length; i++) { 182 sum += (a[i] - avg) * (a[i] - avg); 183 } 184 return sum / (a.length - 1); 185 } 186 187 /** 188 * Return population variance of array, NaN if no such value. 189 */ 190 public static double varp(double[] a) { 191 if (a.length == 0) return Double.NaN; 192 double avg = mean(a); 193 double sum = 0.0; 194 for (int i = 0; i < a.length; i++) { 195 sum += (a[i] - avg) * (a[i] - avg); 196 } 197 return sum / a.length; 198 } 199 200 /** 201 * Return population variance of subarray a[lo..hi], NaN if no such value. 202 */ 203 public static double varp(double[] a, int lo, int hi) { 204 int length = hi - lo + 1; 205 if (lo < 0 || hi >= a.length || lo > hi) 206 throw new RuntimeException("Subarray indices out of bounds"); 207 if (length == 0) return Double.NaN; 208 double avg = mean(a, lo, hi); 209 double sum = 0.0; 210 for (int i = lo; i <= hi; i++) { 211 sum += (a[i] - avg) * (a[i] - avg); 212 } 213 return sum / length; 214 } 215 216 217 /** 218 * Return sample standard deviation of array, NaN if no such value. 219 */ 220 public static double stddev(double[] a) { 221 return Math.sqrt(var(a)); 222 } 223 224 /** 225 * Return sample standard deviation of subarray a[lo..hi], NaN if no such value. 226 */ 227 public static double stddev(double[] a, int lo, int hi) { 228 return Math.sqrt(var(a, lo, hi)); 229 } 230 231 /** 232 * Return sample standard deviation of array, NaN if no such value. 233 */ 234 public static double stddev(int[] a) { 235 return Math.sqrt(var(a)); 236 } 237 238 /** 239 * Return population standard deviation of array, NaN if no such value. 240 */ 241 public static double stddevp(double[] a) { 242 return Math.sqrt(varp(a)); 243 } 244 245 /** 246 * Return population standard deviation of subarray a[lo..hi], NaN if no such value. 247 */ 248 public static double stddevp(double[] a, int lo, int hi) { 249 return Math.sqrt(varp(a, lo, hi)); 250 } 251 252 /** 253 * Return sum of all values in array. 254 */ 255 public static double sum(double[] a) { 256 double sum = 0.0; 257 for (int i = 0; i < a.length; i++) { 258 sum += a[i]; 259 } 260 return sum; 261 } 262 263 /** 264 * Return sum of all values in subarray a[lo..hi]. 265 */ 266 public static double sum(double[] a, int lo, int hi) { 267 if (lo < 0 || hi >= a.length || lo > hi) 268 throw new RuntimeException("Subarray indices out of bounds"); 269 double sum = 0.0; 270 for (int i = lo; i <= hi; i++) { 271 sum += a[i]; 272 } 273 return sum; 274 } 275 276 /** 277 * Return sum of all values in array. 278 */ 279 public static int sum(int[] a) { 280 int sum = 0; 281 for (int i = 0; i < a.length; i++) { 282 sum += a[i]; 283 } 284 return sum; 285 } 286 287 /** 288 * Plot points (i, a[i]) to standard draw. 289 */ 290 public static void plotPoints(double[] a) { 291 int N = a.length; 292 StdDraw.setXscale(0, N-1); 293 StdDraw.setPenRadius(1.0 / (3.0 * N)); 294 for (int i = 0; i < N; i++) { 295 StdDraw.point(i, a[i]); 296 } 297 } 298 299 /** 300 * Plot line segments connecting points (i, a[i]) to standard draw. 301 */ 302 public static void plotLines(double[] a) { 303 int N = a.length; 304 StdDraw.setXscale(0, N-1); 305 StdDraw.setPenRadius(); 306 for (int i = 1; i < N; i++) { 307 StdDraw.line(i-1, a[i-1], i, a[i]); 308 } 309 } 310 311 /** 312 * Plot bars from (0, a[i]) to (i, a[i]) to standard draw. 313 */ 314 public static void plotBars(double[] a) { 315 int N = a.length; 316 StdDraw.setXscale(0, N-1); 317 for (int i = 0; i < N; i++) { 318 StdDraw.filledRectangle(i, a[i]/2, .25, a[i]/2); 319 } 320 } 321 322 323 /** 324 * Test client. 325 * Convert command-line arguments to array of doubles and call various methods. 326 */ 327 public static void main(String[] args) { 328 double[] a = ArrayGenerator.readDouble1D(new In ()); 329 StdOut.format(" min %7.3f\n", min(a)); 330 StdOut.format(" mean %7.3f\n", mean(a)); 331 StdOut.format(" max %7.3f\n", max(a)); 332 StdOut.format(" std dev %7.3f\n", stddev(a)); 333 } 334}