我在Java中执行以下语句,
Obj t[] = new Obj[10];
Obj a = new Obj("a");
t[0] = a;
a = new Obj("b");
t[1] = a;
为什么在java中,当我访问t [0]时,它返回“a”而不是“b”? 这是因为GC吗?我能相信这样做是安全的吗
答案 0 :(得分:10)
这正是发生了什么。
Obj t[] = new Obj[10]; // 1
Obj a = new Obj("a"); // 2
t[0] = a;
a = new Obj("b"); // 3
t[1] = a; // 4
您创建的数组可以容纳10个Obj
实例的引用。请拨打此obj01
。您将其分配给t
。请注意,变量t
和实际对象obj01
之间存在非常随意的关系。
您创建了Obj
的实例,请调用此obj02
。您将此对象的引用分配给变量a
。请注意,变量a
和实际对象obj02
具有非常随意的关系。
您还将此引用放入t[0]
。你有两个地方知道一个对象。对象obj02
(值为"a"
)称为a
,也称为t[0]
。
您创建了Obj
的实例,请调用此obj03
。您将对此新对象的引用分配给旧变量a
。请注意,变量a
和实际对象obj03
具有非常随意的关系。 a
用于引用obj02
,但它不再引用它。
因此,obj01
(数组)由t
引用; obj02
(以及Obj
的实例)称为t[0]
; obj03
(Obj
的一个实例)称为a
。
您将a
中的引用放入t[1]
。因此,t[1]
会获得对obj03
的引用。
此时,所有对象都由范围内的变量引用。由于所有对象都有引用,因此无法对其进行垃圾回收。
答案 1 :(得分:6)
问题是,Java没有指针。
当您将一个对象变量分配给另一个时,它会更改该变量指向的内容,但不会更改您可能拥有的任何其他引用。
所以:
Object a = new Object("a");
Object b = new Object("b");
a = b;
b = new Object("c");
// At this point, a = "b"
// and b = "c"
如您所见,虽然您首先设置a = b,但是当您将b设置为新对象时,仍会保留对旧对象的引用。
答案 2 :(得分:2)
数组中的值只是一个引用。就像这样做:
Obj a = new Obj("a");
Obj t0 = a;
a = new Obj("b");
最后,t0
变量具有第2行给出的值 - 即对第1行创建的第一个Obj
的引用。更改{{1}的值1}}变量不会改变t0的值。
一旦理解了上述内容,只需将数组视为变量集合,例如
a
大致就像声明:
Obj[] t = new Obj[10];
(存在很多差异,但在这个问题的背景下,它们是相似的。)
答案 3 :(得分:1)
当你做t [0] = a;您在数组中分配由新对象(“a”)创建的对象的地址,无论您重复使用该变量,都不会更改数组中包含的值。
答案 4 :(得分:0)
为什么在java中,当我访问t [0]时,它返回“a”而不是“b”?
因为你告诉他用“a”来保存对象的引用。
Java不直接操纵对象。相反,我使用了对象引用。但是这个引用保持引用的值(而不是引用)所以当你为t [0]赋值a时,它们都引用同一个对象。
让我们看看这张照片是否更好地解释了它:
alt text http://img520.imageshack.us/img520/8857/referencesq4.png
首先,a和t [0]引用同一个对象。
稍后引用但是[0]没有。
在结束时a和t 1引用相同的对象,t [0]保持不变。
这是因为GC?
没有
并且我相信这样做是安全的
是