2013-05-31 16 views
2

第三天的C編程讓我忍無可忍。我正在做一個初學者的練習,其中我生成隨機數並計算均值,標準偏差,中位數和模式。在C中計算模式 - 數學有點不對

模式中的問題。我正在繼續研究其他一些項目,但同時我會發布此信息,看看是否有人能夠發現我的錯誤。用戶在開始時輸入隨機數的範圍和它們的數量。如果最小值爲1,則模式返回正確的值,但如果最小值較大,則返回正確的值。

如果對如何允許多個模式有任何見解,我也會很感興趣 - 我有一個近似的想法如何做到這一點(額外的循環和額外的數組?但不是很確定我如何「 d只處理打印新陣列中的相關值)。

這裏的(只的相關部分)我的代碼:

#include <stdio.h> 
#include <stdlib.h> 
#include <time.h> 
#include <math.h> 

int main() { 

    // setting parameters 
    int SIZE, MIN, MAX; 
    printf("How low should the smallest random number be?\n"); 
    scanf("%d",&MIN); 
    printf("How high should the largest random number be?\n"); 
    scanf("%d",&MAX); 
    printf("How many random numbers do you want?\n"); 
    scanf("%d",&SIZE); 

    int rnx[SIZE]; 
    int biggles, *tally, count=0; 
    int mode; 
    int i,j; 
    float mean, sumdev, median; 

    tally = (int*) calloc (MAX-MIN,sizeof(int)); // creates an array for the tally in the mode function and initializes it to zero for the incrementing. 

    srand(time(NULL)); // random seed outside the loop 

    // generate random numbers into an array 

    for(i=0;i<SIZE;i++) { 
    rnx[i]=round(((double)rand()/(RAND_MAX)*(MAX-MIN)+MIN)); 
    } 

    BubbleSort(rnx,SIZE); // left out for brevity the actual function I wrote for this but it works 

    // calculates the mode 

    for(i=MIN;i<MAX;i++) { 
     for(j=0;j<SIZE;j++) { 
      if(rnx[j]==i) { 
       tally[i-MIN]++; // in the second array we register how many times each number occurs in the random sequence, checking from the minimum to maximum. 
      } 
     } 
    } 
    mode = biggles; 
    // for (j=0;j<10;j++) { 
    for(i=MIN;i<MAX;i++) { 
     if(tally[i-MIN]>count) { 
      count=tally[i-MIN]; 
      if(count>1) { 
       mode=i-MIN+1; } 
     } 
    } 

    if (mode!=biggles) { 
    printf("The mode of the random numbers is %d\n",mode); } 
    else { printf("The random numbers have no mode.\n"); } // in case there is no mode. but what if there is more than one? 
    free(tally); 
    return 0; 

} 
+0

我注意到的第一件事是'biggles'永遠不會被初始化,所以當你做'mode = biggles'時''你把'mode'設置爲一個完全隨機的值。(另外,'biggles'不是一個描述性或有意義的名稱。) – Patashu

+0

縮進需要修復。另外,「無模式」意味着一個空的列表。這可能不是檢查它的最好方法。如果您至少有一個號碼,則至少有一種模式。 – xaxxon

+0

@Patashu'不確定'將是比'完全隨機'更好的單詞選擇。 – Dukeling

回答

3

當你這樣做:

tally = (int*) calloc (MAX-MIN,sizeof(int));

說MAX是4,MIN是1,即意味着你可以得到1,2,3和4作爲隨機數。但MAX - MIN = 3,所以你只分配空間3.將其更改爲MAX-MIN + 1。

接下來的問題是這條線。

round(((double)rand()/(RAND_MAX)*(MAX-MIN)+MIN));

再次說MAX是4,MIN是1。這將在任何地方產生的值從1(round(0*(4-1)+1))至4(round(1*(4-1)+1))正確。然而,1到1.5會變成1,而1.5到2.5會變成2,同樣只有3.5到4會變成4.所以1和4是其他數字的一半。

爲了解決這個問題,試試這個,而不是

floor(((double)rand()/(RAND_MAX+1)*(1+MAX-MIN)+MIN));

這將範圍從1到4,但仍然給所有的可能性,平等的機會。 (該RAND_MAX + 1部分,以確保它不會非常微小的概率產生5)

這是我會怎樣計算模式(未經測試):

for (i = 0; i < SIZE; ++i) 
{ 
    tally[rnx[i]-MIN] += 1; 
} 

int modecount = 0; 
int mode = -1; 
for (i = 0; i <= MAX-MIN; ++i) //<= instead of < because MAX is inclusive, not exclusive 
{ 
    if (tally[i] > modecount) 
    { 
     mode = i+MIN; 
     modecount = tally[i]; 
    } 
} 

僞代碼:

1)創建數組,計數每個索引中該數字的隨機數。

2)尋找記錄中最大的記錄並記下它的位置和數量。

然後,處理多種模式:

一旦你通過了tally完全發現的模式,掃描tally尋找具有相同的計數爲你找到了適合自己模式的最高計數的每個條目。所有這些都將是模式,如果您不想分配另一個陣列來存儲它們,則可以將它們打印出來。