我正在创建一个用于向Java数组添加Python功能的数组工具类,我遇到了这个问题。这显然是一个简化的,更通用的版本。
在这个例子中:
public class ArrayTest
{
public static void main(String[] args)
{
// initial setup
int[] given = {1, 2, 3, 4, 5};
// change array
int[] changed = adjust(given);
// these end up being the same...
System.out.println(Arrays.toString(changed));
System.out.println(Arrays.toString(given));
}
private static int[] adjust(int[] a)
{
for (int i = 0; i < a.length; i++)
{
a[i]++;
}
return a;
}
}
...为什么changed
和given
同样如此?
我猜这个问题之前已被问过,但我找不到答案,所以我为此道歉。
答案 0 :(得分:3)
当你这样做时
int[] given = {1, 2, 3, 4, 5};
given
的值称为对象引用。它是一个值告诉JVM该数组在哪里,在内存中的其他位置。 given
不包含数组(就像int
一样),它包含数组的引用(例如,像地址一样) )。 E.g:
+−−−−−−−−−+ [given:Ref88465]−−−−>| (array) | +−−−−−−−−−+ | 0: 1 | | 1: 2 | | 2: 3 | | 3: 4 | | 4: 5 | +−−−−−−−−−+
当您致电adjust(given)
时,您将given
的值副本传递给adjust
。该副本仍然指向内存中的相同位置。例如,在调用adjust
期间,我们有两个该对象引用的副本,两者都指向同一个数组:
+−−−−−−−−−+ [given:Ref88465]−−−−>| (array) | / +−−−−−−−−−+ | | 0: 1 | | | 1: 2 | | | 2: 3 | | | 3: 4 | | | 4: 5 | | +−−−−−−−−−+ [a:Ref88465]−−−−−−+
当您更改数组的内容时,您正在修改数组的状态。当adjust
返回并将结果分配给changed
时,您有:
+−−−−−−−−−+ [given:Ref88465]−−−−−>| (array) | / +−−−−−−−−−+ | | 0: 2 | | | 1: 3 | | | 2: 4 | | | 3: 5 | | | 4: 6 | | +−−−−−−−−−+ [changed:Ref88465]−+
如果您想要更改数组的副本,则需要复制它,例如通过arraycopy
。复制和就地更改都在实践中使用,具体取决于用例。
答案 1 :(得分:0)
你正在做的是将你的数组的地址发送到你的方法,所以更改的是你的原始数组,你只需返回它(你的数组的地址)所以你对该数组所做的任何更改(内存)将反映在两个变量中,因为两者都指向相同的内存位置