2013-02-12 92 views
4

嘿,我很難搞清楚如何計算Java中數組的標準占卜數。正如你所看到的,我已經計算了平均值,而且我知道最後我將不得不除以樣本量減去1(n-1)並平均該數值。我遇到的問題是如何獲取每個數字並計算距離平均值有多遠,然後計算該數字。我知道我可以分別從數據集中完成每個數字,但必須有一個更簡單的方法。任何幫助將不勝感激,這是我的代碼。任何大小數組的標準偏差java

public class CalculateArray 
{ 

    public static void main(String[] args) 
    { 
     int [] numbers = new int[]{1,2,3,4,5,6,7,8,9}; 

     int sum = 0; 
     int max = 0; 
     int min = numbers[0]; 
     double sd = 0; 

     for(int i=0; i<numbers.length; i++) 
     { 
      sum = sum + numbers[i]; 
     } 

     double average = sum/numbers.length; 

     System.out.println("Average value is : " + average); 

     for(int i=0; i<numbers.length; i++) 
     { 
      if(numbers[i] > max) 
      { 
       max = numbers[i]; 
      } 
     } 

     System.out.println("max number is : " + max); 

     for(int i=0; i<numbers.length; i++) 
     { 
      if(numbers[i] < min) 
      { 
       min = numbers[i]; 
      } 
     } 

     System.out.println("min number is : " + min); 

     for (int i=0; i<numbers.length;i++) 
     { 
      //this is where im having problems 
      sd = ??? 
     } 

     double standardDeviation = math.sqrt(sd/(numbers.length-1)); 

     System.out.println("The standard deviation is : " + standardDeviation); 
    } 
} 
+0

'std + = pow(average - numbers [i],2)''? – imreal 2013-02-12 18:20:11

回答

7

要計算一個數字與平均值的差距,請使用-運算符。爲了計算平方,你可以使用Math.pow。因此,鑑於你已經計算早些時候在節目中average

for (int i=0; i<numbers.length;i++) 
{ 
    sd = sd + Math.pow(numbers[i] - average, 2); 
} 

順便說一句,你計算平均值目前被打破的方式。您應該將sum定義爲雙倍,而不是int

+0

您應該使用'Math.abs(數字[i] - 平均數)',否則當'number [i] 2013-02-12 18:29:07

+0

@喬伊,你不需要計算絕對值。 a²= | a |²。 – Joni 2013-02-12 18:30:47

+0

最後,你會想將平方偏差的總和除以數據點的數量。我認爲這是一個均方根;在上面的條款中,rms = sd/numbers.length – criticalfix 2013-02-12 18:32:00

1

除了別人描述的兩遍算法(第一遍和第二遍都計算平均值)之外,請參見this link以獲取如何在單遍中完成的示例。該算法如下:

double std_dev2(double a[], int n) { 
    if(n == 0) 
     return 0.0; 
    double sum = 0; 
    double sq_sum = 0; 
    for(int i = 0; i < n; ++i) { 
     sum += a[i]; 
     sq_sum += a[i] * a[i]; 
    } 
    double mean = sum/n; 
    double variance = sq_sum/n - mean * mean; 
    return sqrt(variance); 
} 

UPDATE
不要這樣做。正如Joni在其下面的comment中解釋的那樣,在實現這個計算機程序時存在很高的錯誤風險。對於一個穩定的在線算法,Joni將我們引導至this維基百科文章,如上所述已經進行了徹底分析。

+2

一個可怕的算法,永遠不要使用。爲什麼它不好,以及有什麼替代方案,請參閱http://www.johndcook.com/blog/2008/09/26/comparing-three-methods-of-computing-standard-deviation/ – Joni 2013-02-13 06:56:54

+0

@Joni感謝您的輸入。這基本上是一個溢出錯誤? – 2013-02-13 19:17:26

+0

問題主要在於'sq_sum/n - mean * mean':它計算兩個大的幾乎相等的數字的差值。數字的取消意味着相對誤差上升 - 您甚至可能以負方差結束。維基百科有關這類數字問題的相當不錯的頁面:http://en.wikipedia.org/wiki/Loss_of_significance – Joni 2013-02-13 19:36:26

0
k + k = 2k 

以獲得平均值,將2k除以您擁有的術語數。 所以術語的平均值是k。 :D