int[][] dp = new int[5][2];
Arrays.fill(dp,new int[]{2,3});
dp[1][0] = 10;
我以为只有dp[1][0]被更改为10,但是所有dp[x][0]都是10(x是从0到4)。我发现了一条与我的问题相关的评论,“这一行使每一行引用相同的内存块,即更改arr[1][5]也将更改arr[100][5]”。那么为什么这些数组对象共享相同的内存呢?它们都在jvm堆或常量池中吗?
相关链接:https://stackoverflow.com/a/19199560/13724489
3条答案
按热度按时间6rvt4ljy1#
当你跑的时候
int[][] dp = new int[5][2];
,得到长度为5的外部数组和长度为2的5个内部数组。所有5个内部数组都填充了0
价值观。当你跑的时候
Arrays.fill(dp,new int[2]{2,3});
,则创建一个长度为2的新数组2
以及3
,然后用新数组的引用填充外部数组的所有5个位置。放弃之前的5个内部数组:这当然意味着
dp[1][0]
以及dp[4][0]
两者都指相同的数组位置,即保持2
价值观。ruarlubt2#
你会这么想吗
Array.fill(dp, new int[2]{2,3})
相当于:但不,更像是:
您只能在该行中创建一个数组
Array.fill(dp, new int[2]{2,3})
. 所有子阵列dp
引用您创建的单个数组。dp[0]
以及dp[1]
以及dp[whatever]
都引用同一数组。这是因为当你调用一个方法时,在方法运行之前,所有的参数都会被计算,所以
new int[2]{2,3}
之前已评估fill
被称为。fill
不“运行”表达式吗new int[2]{2,3}
并将其分配给数组。fill
甚至不知道你用了什么表情!相反,fill
只知道表达式new int[2]{2,3}
求值为-对一个新创建的int数组对象的引用。fill
然后将相同的对象分配给dp
.exdqitrt3#
他们说的是真的:
输出:
[[10, 3], [10, 3], [10, 3], [10, 3], [10, 3]]
在代码中,您只示例化了一个
int[]
(一个一维整数数组)。你在做什么new int[] { 2, 3 })
只有一次。所以只有一个内部数组。这个fill
方法将对同一数组的引用填充到外部数组的每个插槽中。事情就是这样。另外两点
正如holger在评论中所说的,当我们随后构造内部数组时,在声明中构造它们也是一种浪费。省去内部维度,首先只构建外部数组:
顺便说一句,您的这行代码中有一个错误:
不允许同时提供数组维度(长度)和内容。在我的eclipse中,当提供数组初始值设定项时,我无法定义维度表达式。所以别提这个了
2
在方括号中,就像我在上面做的那样。如果需要五个独立的内部数组,可以使用
setAll
方法:现在输出为:
[[2, 3], [10, 3], [2, 3], [2, 3], [2, 3]]
现在发生的是
setAll
电话new int[] { 2, 3 }
对于外部数组的每个索引,创建五个内部数组。