2016-09-21 5 views
1

Мой код вычисляет отклонение населения, когда он мне нужен, чтобы рассчитать отклонение выборки. Я сравнил обе формулы и попытался изменить мои вычисления, но ничего не работает. Благодарим за помощь или вклад каждого.Что изменить в моем коде для расчета образца Стандартное отклонение вместо стандартного deviaiton населения?

public class MeanAndStandardDeviation { 
public static void main (String argv []) throws IOException { 
    BufferedReader stdin = 
      new BufferedReader (new InputStreamReader (System.in)); 
    NumberFormat nf = new DecimalFormat ("0.00"); 
    nf.setMinimumFractionDigits (2);//Sets Min digits 
    nf.setMaximumFractionDigits (2);//Sets Max digits 
    String inputValue; 
    int count = 0; 
    //For Loop for count 
    for(int i = 0; i < count; i++){ 
     count++; 
    } 
    double varianceFinal = 0; 
    List<String> input = new ArrayList<String>();//String ArrayList 
    List<Double> numbers = new ArrayList<Double>();//Double ArrayList 

    //While loop that takes in all my input and assigns it to the ArrayLists 
    //Parameters set for when null is entered and total numbers go over 500 
    while((inputValue = stdin.readLine()) != null && !inputValue.equals("") && input.size()<500){//Parameters set for when null is entered and total numbers go over 500 
     input.add(inputValue); 
     numbers.add (Double.parseDouble(inputValue)); 
    } 

System.out.println ("Standard Deviation: " +(nf.format(calcStdDev (numbers, count, varianceFinal))));//Prints the Standard Deviation 
} 

//StandardDeviation Class 
static double calcStdDev (List<Double> numbers, int count, double variance){ 
    variance = 0; 
    double sum = 0; 
    for(int i = 0; i < numbers.size(); i++){ 
     sum += numbers.get(i); 
     variance += numbers.get(i) * numbers.get(i); 
     count++; 
    } 
    double varianceFinal = ((variance/count)-(sum*sum)/(count*count)); 
return Math.sqrt(varianceFinal); 

} 
} 
+0

Кстати, мой Стандартный класс отклонения находится внизу – swaguire

+0

Только для записи: будьте точны о наименовании: у вас есть два статических ** метода **, а не классы. – GhostCat

+0

Благодарим вас за это – swaguire

ответ

2

Серьезно, ваш код является «неправильным» на многих уровнях. Поэтому вместо того, чтобы отлаживать все это для вас, я дам вам несколько советов, как исправить и упростить код - тогда вам будет очень легко исправить/решить вашу актуальную математическую задачу.

Прежде всего, ваш код так написано в запутанном стиле, который просто делает его гораздо труднее понять (и, следовательно, отладки), чем это должно быть.

Пример:

int count = 0; 
//For Loop for count 
for(int i = 0; i < count; i++){ 
    count++; 
} 

Это цикл не делает ничего . И даже когда условие будет чем-то другим, например i < someNumber; вам все равно нужно будет поставить count = someNumber; вместо петли!

То же самое: что дает счет как аргумент вашим методам? А потом просто увеличить его? Итак, давайте перепишем, что:

public static double calcStdDev (List<Double> numbers, double variance) { 
    double sumOfNumbers = 0; 
    double sumOfSquares = 0; 
    for(double number : numbers) { 
    sumOfNumbers += number; 
    sumOfSquares += number * number; 
} 
... and instead of calculating count, you simply have 
int numberOfNumbers = numbers.size(); 
... and now, do your math 

Другое дело, что действительно странно в вашем коде, как вам настроить ваш дисперсия переменной; и как он используется в ваших методах calc.

Короче говоря: отступите назад и удалите все, что от вашего кода, который не требуется.

+0

Спасибо за советы и помощь, жаль, что это было так плохо :( – swaguire

+0

Добро пожаловать. Я надеюсь, что мои мысли помогут вам в правильном направлении и достаточно, чтобы, наконец, решить вашу проблему. – GhostCat

+0

Да, да, снова спасибо и жаль, что было так плохо, я все еще учился – swaguire

0

Плохая идея вычислить дисперсию, как и вы. Если среднее значение велико, например, 10 миллионов, а шум является небольшим, например, около 1, то ограниченная точность удвоений может означать, что ваша вычисленная дисперсия отрицательна и sd будет нан.

Вы должны либо вычислить его в два прохода, например

double mean = 0.0; 
    for(i=0; i<n; ++i) 
    { mean += x[i]; 
    } 
    mean /= n; 
double var = 0.0; 
    for(i=0; i<n; ++i) 
    { 
    double d = x[i] - mean; 
     var += d*d; 
    } 
    var /= n; 

или за один проход, например

double mean = 0.0; 
double var = 0.0; 
    for(i=0; i<n; ++i) 
    { 
    double f = 1.0/(i+1); 
    double d = x[i]-mean; 
     mean += d*f; 
     var = (1.0-f)*(var + f*d*d); 
    } 

(она занимает немного утомительной алгебры, чтобы показать, что метод один проход дает тот же ответ, что и метод с двумя проходами).