-3

配列サイズを変数で宣言すると ArrayIndexOutOfBoundsException が発生しますが、数値で宣言すると発生しません。

    static Student[] readFile(String filename) {
    .........

    LineNumberReader lnr = null;
    try {
        lnr = new LineNumberReader(new FileReader(new File(filename)));
        lnr.skip(Long.MAX_VALUE);
        len = lnr.getLineNumber();
        lnr.close();
    } catch (IOException e1) {
        e1.printStackTrace();
    }

    len--; // discount the first line
    len = (len > 40) ? 40 : len;
    Student[] s = new Student[len]; <------- replacing len with a number resolves it

    try {
        f = new BufferedReader(new FileReader(new File(filename)));
        while ((line = f.readLine()) != null) {
            ......... 

            s[roll] = new Student(SID, marks); <--- Exception thrown here
            roll++;

            if (roll == 41) {
                f.close();
                throw new CustomException("41st Student!!");
            }
        }
        f.close();

    } catch (IOException e) {
        e.printStackTrace();
    } catch (CustomException e) {
        System.out.println("Too many students in the class!");
    }

    return s;
}

コンパイラ自体が境界を認識していないのに、コンパイラが境界を超えていると考えている理由を誰かが説明してもらえますか?

ありがとう!

4

5 に答える 5

4

ArrayIndexOutOfBoundsExceptionRuntimeException です。それが発生した場合、あなたは確実に限界を超えています。する前に
確認してください。roll < lens[roll] = new Student(SID, marks);

また、Java (およびほとんどの言語) では配列がzeor ベースであることにも注意してください。したがって、 size の配列がある場合N、インデックスは0~ からN - 1(の合計N) になります。

于 2013-09-09T09:26:34.850 に答える
0
  1. 変数「len」はどこで定義しましたか? そして、どのタイプがありますか?「int」にする必要があります
  2. 変数「ロール」はどこから来たのですか? ロールがあるのはどのタイプ?も「int」にする必要があります

配列インデックスには必ず int 値を使用してください。多くの単純型は int に自動キャストできますが、予期しない結果になる可能性があります。

「ロール」が配列サイズより大きくならないようにしてください。

配列のインデックスは 0 から始まることに注意してください。しかし、サイズは1つです。最終的には次のようになります。

String[] myArr = new String[5];
myArray.length == 5
myArray[0] == First entry
myArray[4] == Last entry!!!

単純なループ:

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

それが役に立てば幸いですが、通常はステップデバッガーがこのような質問に答えるはずです。

于 2013-09-09T09:34:04.457 に答える
0
len = (len > 40) ? 40 : len;

len の値には 2 つのケースがあり、どちらも範囲外の例外につながる可能性があります。

を。上記のステートメントが実行された後、len が値 40 に初期化されていると仮定します。この場合、s という配列の長さは 40 です。

s[roll] = new Student(SID, marks);

ロールの値が 40 であると仮定します。次に、値をインデックス 40 に割り当てます。つまり、s[40] = 値です。インデックスの有効な範囲は 0 ~ 39 です。したがって、ArrayIndexOutOfBoundsException がスローされます。

b. len が 40 未満であると仮定します。

s[roll] = new Student(SID, marks); 

ここで、len のサイズより大きい値をインデックスに割り当てるとすぐに、ArrayIndexOutOfBoundsException が発生します。

提案:次のように、ステートメントで値を割り当てる前に、配列サイズが許容範囲内にあることを確認するテストを追加します。

if(roll < len)
{
    s[roll] = new Student(SID, marks); 
}
于 2013-09-09T09:40:48.537 に答える
0
len = (len > 40) ? 40 : len;

ここでは、配列の長さの上限を 40 に設定しています。ファイルに 40 行を超える行が含まれている場合、ここで arrayOutofBound 例外が発生します。

 s[roll] = new Student(SID, marks); <--- Exception thrown here

ファイルが 40 行を超えることはないと確信していますか。そうでない場合は、以前に誰かが指摘したように、比較を逆にします。

     len = (len > 40) ? len : 40;
于 2013-09-09T09:31:20.973 に答える