2017-06-26 3 views
0

単純なBrainTrainアプリケーションを作成すると、updateAnswerメソッドは質問にランダムな回答を出しますが、optionsPressedメソッドを呼び出してオブジェクトを取得しようとすると、問題が発生します。arrayListはIndexOutOfBoundsExceptionを出します。なぜオプションは、optionPressedメソッドと呼ばれるときarraylist自体を空にする?

package com.example.nishantsaini.braintrain; 

import android.graphics.Color; 
import android.graphics.drawable.ColorDrawable; 
import android.graphics.drawable.Drawable; 
import android.os.CountDownTimer; 
import android.support.v4.content.ContextCompat; 
import android.support.v7.app.AppCompatActivity; 
import android.os.Bundle; 
import android.util.Log; 
import android.view.View; 
import android.widget.Button; 
import android.widget.LinearLayout; 
import android.widget.TextView; 

import java.util.ArrayList; 
import java.util.Random; 

import static android.R.color.black; 
import static android.R.color.holo_blue_bright; 
import static android.R.color.holo_blue_dark; 
import static android.R.color.holo_blue_light; 
import static android.R.color.holo_green_light; 



public class MainActivity extends AppCompatActivity { 

Random rnd = new Random(); 
boolean gameisActive = false; 
int count = 0; 
CountDownTimer cd; 
int var1,var2; 
ArrayList<Button> options; 




@Override 
protected void onCreate(Bundle savedInstanceState) { 
    super.onCreate(savedInstanceState); 
    setContentView(R.layout.activity_main); 
    cd = new CountDownTimer(30000, 1000) { 
     @Override 
     public void onTick(long l) { 
      Log.i("Time Left:", Long.toString(l/1000)); 
      TextView timer = (TextView) findViewById(R.id.timer); 
      timer.setText("0:" + String.format("%02d", (l/1000))); 

     } 

     @Override 
     public void onFinish() { 
      TextView score = (TextView) findViewById(R.id.Score); 
      LinearLayout onFinishLayout = (LinearLayout) findViewById(R.id.onFinishLayout); 
      /*score.setText("You got " + getScore() + "right!"); 
      */ 

     } 
    }; 
    options = new ArrayList<>(); 
    options.add((Button) findViewById(R.id.option2)); 
    options.add((Button) findViewById(R.id.option1)); 
    options.add((Button) findViewById(R.id.option3)); 
    options.add((Button) findViewById(R.id.option4)); 
} 

public void start(View view) { 



    cd.start(); 

    Button start = (Button) findViewById(R.id.start); 
    updateQuestion(); 
    updateAnswers(options); 

    start.setText("Replay"); 

} 

public void optionPressed(View view){ 

    ColorDrawable blue_d = new ColorDrawable(getResources().getColor(R.color.blue_b)); 
    ColorDrawable blue_l = new ColorDrawable(getResources().getColor(R.color.blue_l)); 
    ColorDrawable blue_b = new ColorDrawable(getResources().getColor(R.color.blue_b)); 
    ColorDrawable green = new ColorDrawable(getResources().getColor(R.color.green)); 

    Drawable color = blue_b; 
    while(options.size() > 0) { 
     int index = rnd.nextInt(options.size()); 
     Button b = options.get(index); 

     if (color == blue_b){ 
      color = blue_d; 
      b.setBackground(color); 
     } 
     else if (color == blue_d){ 
      color = green; 
      b.setBackground(color); 

     } 
     else if (color == green){ 
      color = blue_l; 
      b.setBackground(color); 

     } 
     else if (color == blue_l) 
     { 
      color = blue_b; 
      b.setBackground(color); 
     } 
     options.remove(index); 
    } 

    updateQuestion(); 
    updateScore(); 
    updateAnswers(options); 

} 

public void updateQuestion(){ 
    var1 = 5 + (int)(Math.random()*20); 
    var2 = 5 + (int)(Math.random()*20); 
    TextView question = (TextView) findViewById(R.id.question); 
    question.setText(Integer.toString(var1) +" + " + Integer.toString(var2) + " = "); 
    question.setPadding(0,50,0,0); 
} 

public void updateScore(){ 

    count++; 
    int correct = 0; 
    TextView score = (TextView) findViewById(R.id.points); 
    score.setText(Integer.toString(correct) + "/" + Integer.toString(count)); 
} 

public void updateAnswers(ArrayList<Button> arrayList){ 

    Button b; 
    int answer = var1 + var2; 
    int indexAtWhichRealAnswerGoes = 1+ (int) (Math.random()*3); 
    int id ; 
    Log.i("arraylist size",Integer.toString(options.size())); 

    b = arrayList.get(indexAtWhichRealAnswerGoes); 
    b.setText(Integer.toString(answer)); 
    id = b.getId(); 
    arrayList.remove(indexAtWhichRealAnswerGoes); 
    for (int i = 0; i < arrayList.size(); i++) { 
     int randomanswer = (answer-7) + (int)(Math.random()*(answer+7)); 
     b = arrayList.get(i); 
     b.setText(Integer.toString(randomanswer)); 

    } 
    arrayList.add((Button) findViewById(id)); 
    Log.i("arraylist size",Integer.toString(arrayList.size())); 

} 
} 
+1

に影響がなくても、リストcopyOptionsを更新することができますが、私は、これは 'int型indexAtWhichRealAnswerGoes = 1+(int型から来賭けます)(Math.random()* 3); "while(options.size()> 0){.. options.remove(randomIndex);}'で空になったリスト上のロジックを確認してください。しかし、そのリストからすべてのオプションを明確に削除しています。 – AxelH

+0

ここから 'optionPressed'メソッドを呼び出します。 –

+1

例外に付随する詳細メッセージとスタックトレースは、コードの前であっても、見るべき最初のものです。あなたが私たちの助けを望むなら、少なくともそれらを提供してください。しかし、一般的には、[mcve]が必要です。これはGUIアプリケーションから生成するのがやや難しいかもしれませんが、プラス面では、それを構築するプロセスは、あなた自身でエラーを発見するのにまともなチャンスを持っています。 –

答えて

0

だから、あなたはあなたが以前にその時点で

while(options.size() > 0) { 
    int index = rnd.nextInt(options.size()); 
    ... 
    options.remove(index); 
} 
... 
updateAnswers(options); 

を空リストを使用してupdateAnswers(options);を呼び出し、リストは空です。この方法で

は、あなたが安全に任意のエラーを防ぐためにfor (int i = 0; i < arrayList.size(); i++) {を使用しますが、その前に、我々はあなたがリストのサイズを確認せず、ランダムインデックスを取得

int indexAtWhichRealAnswerGoes = 1+ (int) (Math.random()*3); 
... 
b = arrayList.get(indexAtWhichRealAnswerGoes); 

を参照してください。 (その時点で空であるList)。


あなたは、その値とリストを維持したいが、removeが必要であるので、ロジックが変更することはできません、あなたはその1つの上で動作するように、リストのコピーを行うには、渡す必要がある場合メソッドupdateAnswersにオリジナル。

List<Button> copyOptions = new ArrayList<>(options); 

それは同じインスタンスを共有しますが、あなたは、スタックトレースを投稿してくださいoptions

+0

これは完璧に働きました、ありがとう –

関連する問題