2016-11-14 118 views
2

我越来越奇怪的行为 - 当我将一个单独的值赋给锯齿阵列时,它会更改整列的值。F#锯齿阵列分配

let testArray = Array.create 5 (Array.create 5 nan) 
testArray.[3].[3] <- 1.0 

上面的代码不是更改单个单元格的值,而是更改整列的值。

val it : float [] [] = 
    [|[|nan; nan; nan; 1.0; nan|]; [|nan; nan; nan; 1.0; nan|]; 
    [|nan; nan; nan; 1.0; nan|]; [|nan; nan; nan; 1.0; nan|]; 
    [|nan; nan; nan; 1.0; nan|]|] 
+2

[Array.create和锯齿状排列]的可能的复制( http://stackoverflow.com/questions/34252606/array-create-and-jagged-array) –

回答

12

这是因为你没有创建一个2维数组(我假定你期望的),而是要创建恰好两个数组:它有5 nan■一个阵列,和另一个数组有5个引用它的第一个数组。只是为了说明这个问题,下面的代码是完全等同于你:

let firstArray = Array.create 5 nan 
let testArray = Array.create 5 firstArray 
testArray.[3].[3] <- 1.0 

使该行testArray.[3].[3] <- 1.0实际上改变只有一个元素 - 第四个在firstArray,但如果然后尝试打印出testArray,该相同的元素会多次出现,因为有多个对firstArray的引用。

如果你想在这五个不同的阵列创建一个数组,你需要使用Array.init,元素的替代,这需要“创造下一个元素”功能:

let testArray = Array.init 5 (fun _ -> Array.create 5 nan) 

或者,你可以使用列表理解创建阵列:

let testArray = [|for i in 1..5 -> Array.create 5 nan|] 

两者都会给你相同的结果,虽然第一个将有更好的性能。

如果你真的需要用二维数组(而不是数组的数组)的工作,你可能想在Array2D寻找替代:

let testArray = Array2D.create 5 5 nan 
testArray.[3,3] <- 1.0