0

I thought I had this figure out, and I was pretty confident it was going to work. Unfortunately, it did not.

The code below is supposed to return the average, the number of values entered and then calculate the std Var. I get it to return the average and count, but the std var result is off. Using the values 5, 6, 8 and 9 I am supposed to get a result of std var 1.83, I am getting something way off 7.17.

I know my error is in the way I am calculating the std Dev, but I was pretty sure I was doing it right.

Here is my code:

/**
This class is used to calculate the average and standard deviation
of a data set.
*/

public class DataSet{

    private double sum;
    private double sumSquare;
    private int counter;

    /**Constructs a DataSet object to hold the
     * total number of inputs, sum and square
     */

    public DataSet(){

        sum = 0;
        sumSquare = 0;
        counter = 0;
    }

    /**Adds a value to this data set
     * @param x the input value
     */

    public void add(double x){

        sum = sum + x;
        sumSquare = sumSquare + x * x;
        counter++;

    }

    /**Calculate average of dataset
     * @return average, the average of the set
     */

    public double getAverage(){

        double avg = sum / counter;

        return avg;

    }

    /**Get the total inputs values
     * @return n, the total number of inputs
     */

    public int getCount(){

        return counter;

    }


    public double getStandardDeviation(){

        double sqr = sumSquare / counter;
        double stdDev = Math.sqrt(sqr);


        return stdDev;


    }
}

Here is my runner program:

import java.util.Scanner;

class DataSetRunner 

{

    public static void main(String[] args)

    {

        Scanner input = new Scanner(System.in);
        DataSet data = new DataSet();

        boolean done = false;
        while (!done)

        {

            System.out.println("Enter value, Q to quit: ");
            String userInput = input.next();
            if (userInput.equalsIgnoreCase("Q"))
             done = true;

             else

             {

                 double x = Double.parseDouble(userInput);
                 data.add(x);

             }

        }

        System.out.println("Average = " + data.getAverage());
        System.out.println("Count = " + data.getCount());
        System.out.println("The Standard Deviation is = " + data.getStandardDeviation());



    }
Jose M.
  • 2,242
  • 8
  • 44
  • 66
  • Don't you need **variance** to get standard deviation? http://en.wikipedia.org/wiki/Standard_deviation – PM 77-1 Jul 29 '13 at 02:08

1 Answers1

4

Your calculation is incorrect.

Standard deviation is based on the sum of the squares of the difference to the mean.

You are simply summing the squares of the data values.

You must first calculate the mean (ie the average), then once you know that you can calculate the standard deviation using this value.

The correct procedure is (quoting from wikipedia):

To calculate the population standard deviation, first compute the difference of each data point from the mean, and square the result of each:

Next, compute the average of these values, and take the square root:

Basically, you can't calculate the standard deviation "as you go".

Community
  • 1
  • 1
Bohemian
  • 412,405
  • 93
  • 575
  • 722
  • 1
    Sure you can. http://stackoverflow.com/questions/5543651/computing-standard-deviation-in-a-stream#comment6301752_5543651 – James McLeod Jul 29 '13 at 02:19
  • @JamesMcLeod No, you can't. You can do a *complete recalculation* every time you add a value, but that's hardly counts as the "on the fly", and you certainly can't store any calculations made of the fly to use again for the next addition of a value. – Bohemian Jul 29 '13 at 04:49