Warning: file_get_contents(/data/phpspider/zhask/data//catemap/5/ruby-on-rails-4/2.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
数组在Java中似乎是通过引用传递的,这怎么可能呢?_Java_Arrays_Pass By Reference - Fatal编程技术网

数组在Java中似乎是通过引用传递的,这怎么可能呢?

数组在Java中似乎是通过引用传递的,这怎么可能呢?,java,arrays,pass-by-reference,Java,Arrays,Pass By Reference,如果需要,我可以发布更多的代码,但在此之前,我想问一个关于以下方法的一般性问题,其中一个数组被传递,然后设置为另一个数组,但由于某种原因,原始数组(被传递的数组)也被更改,这怎么可能/我应该怎么做? 谢谢 tempBoard是一个与currentState大小相同的数组,temp[k]包含在movePiece中进行的更改,当前状态在方法中声明,不是全局变量 private int[][] MiniMaxBaseCase(int[][] currentState, int currentColor

如果需要,我可以发布更多的代码,但在此之前,我想问一个关于以下方法的一般性问题,其中一个数组被传递,然后设置为另一个数组,但由于某种原因,原始数组(被传递的数组)也被更改,这怎么可能/我应该怎么做? 谢谢

tempBoard是一个与currentState大小相同的数组,temp[k]包含在movePiece中进行的更改,当前状态在方法中声明,不是全局变量

private int[][] MiniMaxBaseCase(int[][] currentState, int currentColor)
{
    tempBoard = movePiece(currentState,temp[k]);
}

private int[][] movePiece(int[][] currentState, int[] move)
{
    if(move[0] == -1)
        return currentState;

    //if the piece is just moving
    if(move[4] == -1)
    {
        currentState[move[2]][move[3]] = currentState[move[0]][move[1]];
        currentState[move[0]][move[1]] = 0;
        return currentState;
    }

    //if the piece is jumping another
    if(move[4] != -1)
    {   
        currentState[move[4]][move[5]] = currentState[move[0]][move[1]];
        currentState[move[2]][move[3]] = 0;
        currentState[move[0]][move[1]] = 0;
        return currentState;
    }

    return currentState;
}
在Java中:

  • 方法参数确实是按值传递的,但是
  • Java中的所有对象和数组变量都是引用变量
引用变量按值传递的净效果是该引用变量指向的对象或数组按引用传递。

您的数组实际上是通过引用传递的-它是同一个数组

具体来说,
MiniMaxBaseCase
中的
currentState
是对数组的引用-它的值是数组的内存位置<
MiniMaxBaseCase
中的code>currentState通过值传递给
movePiece
,因此
MiniMaxBaseCase
中的
currentState
的值(内存位置)如果复制到
movePiece
中的参数
currentState
,则引用通过值传递。但是现在
movePiece
中的
currentState
指向与
MiniMaxBaseCase
中的
currentState
相同的内存位置。所以现在两个变量都指向同一个数组,也就是说,净效应是数组通过引用有效地传递


编辑:复制多维数组

一些人建议直接使用
System.arraycopy()
Array.copyOf()
,而不必遍历第一个维度/索引。这行不通

改用这个:

public static int[][] copyOf(int[][] original) {
    int[][] copy = new int[original.length][];
    for (int i = 0; i < original.length; i++) {
        copy[i] = Arrays.copyOf(original[i]);
    }
    return copy;
}
public static int[]copyOf(int[]original){
int[][]复制=新的int[original.length][];
对于(int i=0;i
直接复制不起作用的原因是,在Java中,二维数组实际上是指向一组(分散的)一维数组的指针/引用数组,即,
int[][]
是指向一组(分散的)
int[]
的指针数组。只需在二维数组上执行
System.arraycopy()
Arrays.copyOf()
即可将指针复制到分散的
int[]
Arrays
,即此浅层副本最终共享底层数组集。您必须按照上面的代码进行深度复制

一些参考资料:

是的,您应该在2D布尔数组上迭代以进行深度复制


如何复制多维数组

。。。 但是,复制二维数组的问题更大,因为多维数组表示为数组的数组。克隆阵列时会出现此问题。System.arraycopy()将为您提供一份对嵌入式阵列的引用副本


花点时间好好读一读

跳到“传递数组”

数组是引用。这意味着当我们将数组作为参数传递时,我们传递的是它的句柄或引用。因此,我们可以在方法内部更改数组的内容

这是一门课程“148:计算机科学导论”,它应该与Java语言的前两节课相适应

要将数组的副本传递给函数,在Java1.6中,可以使用array.copyOf,例如

tempBoard = movePiece(Arrays.copyOf(currentState, currentState.length), temp[k]);

注意:
数组。copyOf
仅适用于原语的一维数组。在其他任何情况下,它都会提供一个独立的数组,所有元素都相同并指向原始数组,无论是对象还是嵌套数组。

在Java中,没有“按引用传递”这样的东西。你似乎知道这一点,并想知道为什么这里仍然会发生这样的事情

问题是,数组是对象。对象实际上是指针。因此,您得到了指向数组的指针的副本,但它仍然是它所指向的数组


如果要在对数组进行任何更改之前创建该数组的副本,请使用System.arraycopy()。

数组是对象。对象是引用类型。这并不奇怪。根据我到目前为止所看到的所有地方,在java中不可能通过引用传递,但是,可以通过值传递对象引用。这两者之间的区别是什么。Jon的网站似乎对我来说已经关闭了,但这里有一个缓存链接:那么我该怎么做才能使它不改变原来的内容呢?就像你对对象引用所做的一样——你不想碰它的对象:首先克隆对象。@Jeremy-我相信
System.arraycopy()
将在需要深度复制的地方进行浅层复制。@Bert F-Nice,我想我从来都不需要复制二维数组。好东西。我相信这个
copyOf
会做二维数组的浅拷贝,而不会创建完全独立于原始数组的数组的真正深度拷贝。@BertF:引用类型的数组封装其中包含的对象的标识,以及它们的状态的不可变方面,但不封装其状态的任何可变方面。一个数组包含对其可变状态初始化为源数组中相应成员的可变状态的对象的引用,它实际上不是源数组的副本,而是完全其他的东西。您可能需要指出,在二维数组上使用
System.arraycopy()
时要小心—使用起来很幼稚,最终将得到一个浅层副本,它不是原始阵列的独立副本。