2009-08-15 22 views
2

我正在學習一個初學Java類,用以下輸出創建直方圖程序:(100和10是用戶輸入)。開始Java(直方圖)

有多少個數字? 100 多少間隔? 10

Histogram 
-------------------------------------------------------- 
    1 ****(4) 
    2 ******(6) 
    3 ***********(11) 
    4 *****************(17) 
    5 **************************(26) 
    6 *************************(25) 
    7 *******(7) 
    8 ***(3) 
    9 (0) 
10 *(1) 
-------------------------------------------------------- 

我的代碼給出了以下輸出,但是,誰能幫我指出哪裏出了問題,非常感謝。

How Many Numbers? 10 
How Many Intervals? 10 

Histogram 
-------------------------------------------------------- 
1 **********(10) 
2 **********(10) 
3 **********(10) 
4 **********(10) 
5 **********(10) 
6 **********(10) 
7 **********(10) 
8 **********(10) 
9 **********(10) 
10 **********(10) 

對於輸入,100和10我得到的錯誤消息:在線程 「主」 java.lang.ArrayIndexOutOfBoundsException

例外:10 在Lab6.main(Lab6.java:44 )我在下面標出了第44行。

鏈接到此代碼的鏈接;

   intervalValue[j]++; 

我不知道如何安裝發電機(的.jar)文件,它應該只生成隨機#的我們。再次感謝。

mport java.util.Scanner; 

public class Lab6 { 

    public static void main(String[] args) { 

     int numbers, intervals; 
     double intervalWidth; 

     double max, mins, range; 

     Scanner keyboard = new Scanner(System.in); 

     System.out.print("How Many Numbers? "); 

     numbers = keyboard.nextInt(); 

     System.out.print("How Many Intervals? "); 

     intervals = keyboard.nextInt(); 

     double [] generate = new double[numbers]; 

     generate = randomGenerator(numbers); 

     max = maximum(generate); 

     mins = minimum(generate); 

     range = max - mins; 

     intervalWidth = range/intervals; 

     int [] intervalValue = new int[intervals]; 

     for (int i=0; i < generate.length; i++) { 

      for (int j = 0; j<generate.length; j++){ 
       double imin = mins+j*intervalWidth; 
       double imax = max +j*(intervalWidth); 
       if(generate[i] >= imin && generate[i] < imax) 
        intervalValue[j]++;   //LINE 44 
      } 
     } 

     System.out.println("Histogram"); 

     System.out.println("--------------------------------" + 
          "------------------------"); 

     for (int a=0; a < intervalValue.length; a++) { 

      System.out.print(" " + (a+1) + " "); 

      for (int b=0; b < intervalValue[a]; b++) { 
       System.out.print("*"); 
      } 

      System.out.println("(" + intervalValue[a] + ")"); 
     } 
    } 

    private static double [] randomGenerator(int number) { 
     double [] generate; 

     generate = Generator.getData(number); 

     return generate; 
    } 

    private static double maximum(double [] a) { 

     double max = a[0]; 

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

     return max; 
    } 

    private static double minimum(double [] a) { 

     double mins = a[0]; 

     for (int i = 1; i < a.length; i++) { 
      if (a[i] < mins) { 
       mins = a[i]; 
      } 
     } 

     return mins; 
    } 
} 
+0

可惜我不能沒有你生成類編譯它打印出來。 – Kekoa 2009-08-15 23:47:00

+1

,你可能想考慮使用代碼格式化程序(eclipse有一個內置的)也不會嘗試發佈二進制文件的內容。它沒有幫助:) – 2009-08-16 00:11:40

回答

0

使用像eclipse這樣的IDE,運行你的程序,看看第44行是哪裏。這就是你得到你的ArrayIndexOutOfBoundsException的地方,那就是你需要確保你沒有退出債券的地方。 在java中的數組有第一個項目在索引0,所以一個數組10個項目將使它們編號爲0,1,2,3,4,5,6,7,8,9。如果它發生在10,你可能會迭代一步。 確保當你到達那裏時,「intervalValue [j]」中的j不是10。

既沒有完整的例外,也沒有編輯源代碼,也沒有在你粘貼的源代碼中更正行號。沒有太多的事情要做。弄清楚它會幫助你獲得與實驗室其他人員一樣多的知識。給它一個很好的嘗試。

2

你需要從線43的末尾移除分號:

if(generate[i] >= imin && generate[i] < imax); 

分號導致你if塊是空的。因此,導致異常的線路將無條件執行。

一旦你解決這個問題,這裏有一些提示,讓你開始在你的代碼的進一步調試:


看看你的內部循環的終止條件:

for (int j = 0; j<generate.length; j++) 

您正在迭代外循環中生成的數字;所以你應該迭代你內部循環的時間間隔來確定每個生成的數字所屬的時間間隔。


看看你的代碼使用,以確定在循環當前間隔的界限:

double imin = mins+j*intervalWidth; 
double imax = max +j*(intervalWidth); 

這些線路需要進行修改,以獲得正確的價值觀。做一些「鉛筆和紙調試」來確定他們爲什麼錯誤。


我現在將剩下的作爲讀者的練習。我稍後會檢查是否需要任何進一步的幫助。

+0

+1好點,錯過了它。 – Fredrik 2009-08-15 16:22:07

0
intervalValue[j]++; 

Ĵ談到上升到數字的數量,但intervalValue從間隔的數量分配的,如果這兩個數字都沒有,你會得到你在這裏看到的錯誤相同。

+0

我怎樣才能讓他們一樣,或者至少不會產生錯誤? - 感謝, – Benzle 2009-08-15 16:31:10

0

您的數組異常似乎是由使用generate.length兩次引起的 - 儘管您的粘貼代碼似乎是由此編輯的。

但是,除此之外,問題在於你的嵌套循環。除了第一個內部循環中錯誤的數組大小之外,你會沿着正確的方向行進。 然後,在if語句中 - 您想增加該值,如果該值處於正確的區間,則該值單獨增加;用你當前的代碼,你每增加一個,就解釋輸出。

以你自己的代碼和註釋:

for (int i=0; i < generate.length; i++) { 

    for (int j = 0; j<intervals; j++){ // could use intervalValues.length here; it's all preference 
    double imin = mins+j*intervalWidth; 
    double imax = mins +(intervalWidth)*(j+1); 
    if(generate[i] >= imin && generate[i] < imax) 
     // for(int j1 = 0; j1 < intervalValue.length; j1++) <- this was causing the bad output 
     /* I assume the j1 from your code was during a debug attempt. Changed back, 
      since the preceeding loop has been removed */ 
     intervalValue[j]++; 


    } 

} 
2

由於我是在一個週六的感覺大方我嘗試過了,並改寫你的循環。

for (int j=0; j < generate.length; j++) { 
    for(int i = 0; i < intervals; i++) { 
     double imin = mins + i * intervalWidth; 
     double imax = mins + (intervalWidth) * (i + 1); 
     if(i == intervals - 1) imax = Double.POSITIVE_INFINITY; 
     if(i == 0) imin = Double.NEGATIVE_INFINITY; 

     if (generate[j] >= imin && generate[j] < imax) { 
      intervalValue[i]++; 
      break; 
     } 
    } 
} 

無窮大的東西是捕捉直方圖中的最小值和最大值。

+0

非常感謝大家,這已經是堆棧溢出的絕佳體驗! – Benzle 2009-08-16 16:08:44

1

這會給你一個非常好的(基本的)外觀直方圖。試試吧

import java.util.HashMap; 
import java.util.Map; 

public class Histogram { 
    public static void main(String[] args) { 
     int[] age = { 25, 26, 33, 26, 27, 21, 26, 33, 21, 33, 21, 38, 19, 19}; 


     HashMap<Integer, Integer> m = new HashMap<Integer, Integer>(); 

     for (int i = 0; i < age.length; i++) { 
      int c = 0; 

      for (int j = 0; j < age.length; j++) { 
       if (age[i] == age[j]) { 
        c++; 
       } 
      } 
      m.put(age[i], c); 

     } 

     System.out.println("Histogram\n------------"); 
     for (Map.Entry<Integer, Integer> entry : m.entrySet()) { 
      int key = entry.getKey(); 
      int value = entry.getValue(); 
      System.out.printf("%3d | ", key); 
      for (int i = 0; i < value; i++) { 
       System.out.print("="); 
      } 
      System.out.print(" " + value); 
      System.out.println(); 
     } 

    } 

Outout:

Histogram 
------------ 
33 | === 3 
19 | == 2 
21 | === 3 
38 | = 1 
25 | = 1 
26 | === 3 
27 | = 1 

我使用HashMap來保持兩個相關值,即一個數組元素,它的頻率(它出現的頻率)。

然後通過使用c變量,通過沿陣列的每個元素循環嵌套循環並計數其頻率。

從那以後,我與for-each循環和正常循環

+0

你能用幾句話解釋代碼嗎?它會讓你的回答變得更好,你可以得到更多的選票。 – Andrei 2014-05-19 14:05:30

+0

我使用HashMap來保持兩個相關的值,即一個數組元素及其頻率(它出現的頻率)。然後一個嵌套的循環由數組中的每個元素循環並使用「c」變量對其頻率進行計數。之後,我用增強型for循環和正常循環打印它 – Amjad 2014-05-20 10:45:50

+0

在解答中添加了解釋。在功能不要忘記解釋你的代碼:)好工作! – Andrei 2014-05-20 11:24:05