ArrayList<;列表<&燃气轮机&燃气轮机;Java中通过引用复制值的变量?
我很困惑 这是我对基本变量和赋值的理解:ArrayList<;列表<&燃气轮机&燃气轮机;Java中通过引用复制值的变量?,java,arraylist,Java,Arraylist,我很困惑 这是我对基本变量和赋值的理解: int a = 9; int b = a; int a = 8; System.out.println(b); // This will be 9 现在我正在尝试同样的方法,但我使用的不是基本类型而是ArrayList二维结构,请参见以下代码: public final class Matrix { private List<List<Double>> rawMatrix = new ArrayList<List
int a = 9;
int b = a;
int a = 8;
System.out.println(b); // This will be 9
现在我正在尝试同样的方法,但我使用的不是基本类型而是ArrayList二维结构,请参见以下代码:
public final class Matrix {
private List<List<Double>> rawMatrix = new ArrayList<List<Double>>();
private List<List<Double>> matrix = new ArrayList<List<Double>>();
private void update(){
matrix = rawMatrix;
System.out.println("matrix: "+matrix.size()+", "+matrix.get(0).size());
System.out.println("matrix: "+rawMatrix.size()+", "+rawMatrix.get(0).size());
matrix.get(0).add(99.0);
System.out.println("matrix: "+matrix.size()+", "+matrix.get(0).size());
System.out.println("matrix: "+rawMatrix.size()+", "+rawMatrix.get(0).size());
}
}
现在出于某种原因,rawMatrix
添加了一个与matrix
相同的元素,尽管我从未在rawMatrix
结构中添加任何内容
我假设这是一种通过引用分配变量的奇怪类型,我不太明白为什么会出现这种情况,为什么它是Java中的默认值
我如何克服这个问题?我是否必须使用两个for循环使我的矩阵中的一个相等于另一个,这似乎非常低效。由于ArrayList是对象,赋值只会将指针复制到该对象。 使用基元类型实际上是在复制值
这意味着你的分配
matrix=rawMatrix代码>使矩阵
指向与rawMatrix
相同的内存位置,当该内存更新时,更改也将反映到矩阵
指向的位置。由于数组列表是对象,分配只需将指针复制到对象即可。
使用基元类型实际上是在复制值
这意味着你的分配matrix=rawMatrix代码>使矩阵
指向与原始矩阵
相同的内存位置,当该内存更新时,更改也将反映到矩阵
点的位置。此行:
matrix = rawMatrix;
制作矩阵
参考原始矩阵
。之后,您只对一个ArrayList
对象有一个引用,并且两个变量都设置为该引用。(我怀疑另一个ArrayList
将无法访问,并且如果您没有在其他地方使用它,它将被gc-ed)这一行:
matrix = rawMatrix;
制作矩阵
参考原始矩阵
。之后,您只对一个ArrayList
对象有一个引用,并且两个变量都设置为该引用。(我怀疑另一个ArrayList
将不可访问,并且会被gc-ed,如果您没有在其他地方使用它的话)update方法中的第一条语句是
matrix=rawMatrix代码>因此,您的参考变量矩阵和原始矩阵都引用列表>的同一对象
因此,尽管您正在使用这两个变量中的任何一个添加元素,但这两个变量都会得到相同的答案,因为它们都引用相同的对象。更新方法中的第一条语句是
matrix=rawMatrix代码>因此,您的参考变量矩阵和原始矩阵都引用列表>的同一对象
因此,尽管您使用这两个变量中的任何一个添加元素,但这两个变量都会得到相同的答案,因为它们都引用相同的对象。因为矩阵是rawMatrix
您创建了两个对象
private List<List<Double>> rawMatrix = new ArrayList<List<Double>>();
private List<List<Double>> matrix = new ArrayList<List<Double>>();
因为矩阵是原始矩阵
您创建了两个对象
private List<List<Double>> rawMatrix = new ArrayList<List<Double>>();
private List<List<Double>> matrix = new ArrayList<List<Double>>();
int是一种基本数据类型。这意味着,当您指定给它时,您将为它指定一个实际值
对象是通过引用指定的。这意味着matrix=rawMatrix
行将设置matrix引用的对象与rawMatrix引用的对象相同
如果要复制对象,必须使用适当的克隆或复制方法,或者创建新对象并自行填充。请记住(在适当的情况下),您可能希望保持“深度”复制阵列本身中的对象。对于这样的嵌套数组,您可能希望复制“内部”列表。int是一种基本数据类型。这意味着,当您指定给它时,您将为它指定一个实际值
对象是通过引用指定的。这意味着matrix=rawMatrix
行将设置matrix引用的对象与rawMatrix引用的对象相同
如果要复制对象,必须使用适当的克隆或复制方法,或者创建新对象并自行填充。请记住(在适当的情况下),您可能希望保持“深度”复制阵列本身中的对象。对于这样的嵌套数组,您可能希望复制“内部”列表。这是有关stackoverflow的常见问题。这将帮助您。这就是java的工作原理。如果您执行anObject=anotherObject
,则表示anObject
具有与anotherObject
相同的引用,因此它们将引用相同的实例。您需要创建一个新的arraylist并将所有数据复制到it@ChrisK,但这个问题是关于方法的,对吗?我知道方法,这里我认为它只是变量。(也许我错了)@joseph,前提是相似的。您以前使用过调试器吗?逐步阅读此代码可能会让您了解它的实际工作方式。具体来说,matrix和rawMatrix指向的是完全相同的实例。这非常接近于-的副本,您可能想在那里阅读我的答案。这是一个关于stackoverflow的常见问题。这将帮助您。这就是java的工作原理。如果您执行anObject=anotherObject
,则表示anObject
具有与anotherObject
相同的引用,因此它们将引用相同的实例。您需要创建一个新的arraylist并将所有数据复制到it@ChrisK,但这个问题是关于方法的,对吗?我知道方法,这里我认为它只是变量。(也许我错了)@joseph,前提是相似的。您以前使用过调试器吗?逐步阅读此代码可能会让您了解它的实际工作方式。具体来说,matrix和rawMatrix指向的是完全相同的实例。这非常接近于-的副本,您可能想在那里阅读我的答案。@Joseph,如果您发现这个答案解决了您的问题,您可以接受它。@Joseph,如果您找到这个答案