Java 为什么arraylist在被称为optionPressed方法时会清空自身?
制作一个简单的BrainTrain应用程序,Java 为什么arraylist在被称为optionPressed方法时会清空自身?,java,android,arraylist,Java,Android,Arraylist,制作一个简单的BrainTrain应用程序,updateAnswer方法会随机给出问题的答案,但每当我调用选项pressed方法并尝试获取任何对象时,问题就会出现,arrayList会发出索引自动边界异常 package com.example.nishantsaini.braintrain; import android.graphics.Color; import android.graphics.drawable.ColorDrawable; import android.graphic
updateAnswer
方法会随机给出问题的答案,但每当我调用选项pressed
方法并尝试获取任何对象时,问题就会出现,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()));
}
}
package com.example.nishantsaini.braintrain;
导入android.graphics.Color;
导入android.graphics.drawable.ColorDrawable;
导入android.graphics.drawable.drawable;
导入android.os.CountDownTimer;
导入android.support.v4.content.ContextCompat;
导入android.support.v7.app.AppActivity;
导入android.os.Bundle;
导入android.util.Log;
导入android.view.view;
导入android.widget.Button;
导入android.widget.LinearLayout;
导入android.widget.TextView;
导入java.util.ArrayList;
导入java.util.Random;
导入静态android.R.color.black;
导入静态android.R.color.holo_blue_bright;
导入静态android.R.color.holo_blue_dark;
导入静态android.R.color.holo_蓝光;
导入静态android.R.color.holo_绿色_灯;
公共类MainActivity扩展了AppCompatActivity{
随机rnd=新随机();
布尔gameisActive=false;
整数计数=0;
倒计时cd;
int-var1,var2;
ArrayList选项;
@凌驾
创建时受保护的void(Bundle savedInstanceState){
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
cd=新的倒计时(300001000){
@凌驾
公共空白条(长l){
Log.i(“剩余时间:”,长串(l/1000));
TextView定时器=(TextView)findViewById(R.id.timer);
timer.setText(“0:+String.format”(%02d),(l/1000));
}
@凌驾
公共无效onFinish(){
TextView得分=(TextView)findViewById(R.id.score);
LinearLayout onFinishLayout=(LinearLayout)findViewById(R.id.onFinishLayout);
/*score.setText(“你得到了”+getScore()+“对!”);
*/
}
};
选项=新的ArrayList();
选项。添加((按钮)findViewById(R.id.option2));
选项。添加((按钮)findViewById(R.id.option1));
选项。添加((按钮)findViewById(R.id.option3));
选项。添加((按钮)findViewById(R.id.option4));
}
公共无效开始(视图){
cd.start();
按钮开始=(按钮)findViewById(R.id.start);
updateQuestion();
更新答案(选项);
start.setText(“重播”);
}
公共作废选项按下(查看){
ColorDrawable blue_d=新的ColorDrawable(getResources().getColor(R.color.blue_b));
ColorDrawable blue_l=新的ColorDrawable(getResources().getColor(R.color.blue_l));
ColorDrawable blue_b=新的ColorDrawable(getResources().getColor(R.color.blue_b));
ColorDrawable green=新的ColorDrawable(getResources().getColor(R.color.green));
可拉伸颜色=蓝色;
while(options.size()>0){
int index=rnd.nextInt(options.size());
按钮b=options.get(索引);
如果(颜色==蓝色){
颜色=蓝色;
b、 挫折背景(颜色);
}
else if(颜色==蓝色){
颜色=绿色;
b、 挫折背景(颜色);
}
else if(颜色==绿色){
颜色=蓝色;
b、 挫折背景(颜色);
}
else if(颜色==蓝色)
{
颜色=蓝色;
b、 挫折背景(颜色);
}
选项。删除(索引);
}
updateQuestion();
updateScore();
更新答案(选项);
}
public void updateQuestion(){
var1=5+(int)(Math.random()*20);
var2=5+(int)(Math.random()*20);
TextView问题=(TextView)findViewById(R.id.question);
question.setText(Integer.toString(var1)+“+”+Integer.toString(var2)+“=”;
问题.设置填充(0,50,0,0);
}
public void updateScore(){
计数++;
int correct=0;
TextView得分=(TextView)findViewById(R.id.points);
score.setText(Integer.toString(correct)+“/”+Integer.toString(count));
}
公共无效更新应答器(ArrayList ArrayList){
按钮b;
int-answer=var1+var2;
int index=1+(int)(Math.random()*3);
int-id;
Log.i(“arraylist size”,Integer.toString(options.size());
b=arrayList.get(返回答案的索引);
b、 setText(整数.toString(答案));
id=b.getId();
arrayList.remove(返回答案的索引);
对于(int i=0;i
因此,您可以调用更新应答器(选项)代码>使用以前清空的列表
while(options.size() > 0) {
int index = rnd.nextInt(options.size());
...
options.remove(index);
}
...
updateAnswers(options);
此时,列表为空
在该方法中,您安全地使用了for(inti=0;i
来防止任何错误,但在此之前我们看到
int indexAtWhichRealAnswerGoes = 1+ (int) (Math.random()*3);
...
b = arrayList.get(indexAtWhichRealAnswerGoes);
您在不检查列表大小的情况下获得该随机索引。(list
此时为空)
如果您希望保留列表及其值,但无法更改逻辑,因此必须执行删除
,则需要复制列表以处理该列表,并将原始列表传递给方法更新应答
List<Button> copyOptions = new ArrayList<>(options);
List copyOptions=new ArrayList(选项);
它将共享同一个实例,但您可以更新列表copyOptions
,而不会对选项产生任何影响请发布堆栈跟踪,但我打赌这来自int indexathWhichrealAnswerGoes=1+(int)(Math.random()*3);…arrayList.get(indexathWhealAnswerGoes);
在while(options.size()>0){..options.remove(randomIndex);}中清空的列表上
检查那里的逻辑。但是您显然正在删除eve