我正在向一个ArrayList中添加三个不同的对象,但该列表包含我添加的最后一个对象的三个副本。
例如:
for (Foo f : list) {
System.out.println(f.getValue());
}
预期:
0
1
2
实际:
2
2
2
我犯了什么错误?
注意:这是针对本网站上出现的众多类似问题而设计的一个规范问答。
您的问题是statice
类型,它需要在每次循环迭代时进行新的初始化。如果您在一个循环中,最好将具体的初始化保留在循环中。
List<Object> objects = new ArrayList<>();
for (int i = 0; i < length_you_want; i++) {
SomeStaticClass myStaticObject = new SomeStaticClass();
myStaticObject.tag = i;
// Do stuff with myStaticObject
objects.add(myStaticClass);
}
而不是:
List<Object> objects = new ArrayList<>();
SomeStaticClass myStaticObject = new SomeStaticClass();
for (int i = 0; i < length; i++) {
myStaticObject.tag = i;
// Do stuff with myStaticObject
objects.add(myStaticClass);
// This will duplicate the last item "length" times
}
这里的tag
是somestaticclass
中的一个变量,用于检查上述代码段的有效性;您可以根据您的用例有一些其他的实现。
这个问题有两个典型的原因:
>
存储在列表中的对象使用的静态字段
意外地将同一对象添加到列表中
如果列表中的对象将数据存储在静态字段中,则列表中的每个对象看起来都是相同的,因为它们持有相同的值。请考虑以下类别:
public class Foo {
private static int value;
// ^^^^^^------------ - Here's the problem!
public Foo(int value) {
this.value = value;
}
public int getValue() {
return value;
}
}
在该示例中,只有一个int value
在foo
的所有实例之间共享,因为它被声明为static
。(请参阅“理解类成员”教程。)
如果使用下面的代码将多个foo
对象添加到列表中,则每个实例将从对GetValue()
的调用返回3
:
for (int i = 0; i < 4; i++) {
list.add(new Foo(i));
}
解决方案很简单--不要对类中的字段使用statice
关键字,除非您实际上希望该类的每个实例之间共享值。
如果向列表中添加临时变量,则每次循环时都必须为所添加的对象创建一个新实例。请考虑以下错误代码段:
List<Foo> list = new ArrayList<Foo>();
Foo tmp = new Foo();
for (int i = 0; i < 3; i++) {
tmp.setValue(i);
list.add(tmp);
}
在这里,tmp
对象是在循环之外构造的。因此,同一个对象实例被添加到列表中三次。实例将保存值2
,因为这是在上次调用setValue()
时传递的值。
要解决这个问题,只需将对象结构移动到循环内部:
List<Foo> list = new ArrayList<Foo>();
for (int i = 0; i < 3; i++) {
Foo tmp = new Foo(); // <-- fresh instance!
tmp.setValue(i);
list.add(tmp);
}
问题内容: 为什么我添加到ArrayList中对象只包N个最后一个元素? 问题答案: 此问题有两个典型的原因: 你存储在列表中的对象使用的静态字段 意外将同一对象添加到列表 静态场 如果列表中的对象将数据存储在静态字段中,则列表中的每个对象将看起来是相同的,因为它们具有相同的值。考虑下面的类: 在该示例中,由于声明了,因此在所有实例之间只有一个共享。(请参阅“了解班级成员”教程。) 如果使用以下代
问题内容: public static void main(String args[]){ 我试图显示上面变量的当前值,并将其与学生对象进行比较 然后我注意到我的Arraylist仅显示一个值: 通常我会阅读100多个项目,但在此示例中,我仅阅读了5个项目;这是程序的输出; 现在,女士们,先生们,我的问题是,我尝试显示Stud对象以检查其读取的值是否正确,并且确实显示正确,然后在为其分配值之后,将
我有两个数据库表
我有一个for循环,它遍历CSV中的每一行,我创建了一个包含列表的字典,但是列表被重写了,因为字典键被重复了几次。我如何总结或追加到列表中的第二(1)位置相同的键的下一个值下一个循环迭代? 因为使用append时,如果再次找到现有键,则会覆盖该值,因此该键的值会被一次又一次地覆盖。 CSV中的字段包括: 输出应该是这样的:
这里是SQL初学者,在我的大学课程中,我们有以下模式。 学生(snum:整数,sname:字符串,专业:字符串,级别:字符串,年龄:整数) 类(名称:字符串,meets_at:字符串,房间:字符串,fid:整数) 已注册(snum:整数,cname:字符串) 教员(fid:整数,fname:字符串,deptid:整数) 其中一个练习如下: 找出同时参加两个班的所有学生的名字。 下面是它的SQL语句
如果一个表达式包含任何整数大小或更小的内容,其结果总是整数,即使两个字节之和适合一个字节。 为什么我们在一个字节中添加最后两个字节时会发生这种情况?没有编译器错误。