function map(f, a) {
for(var i in a) {
a[i] = f(a[i]);
}
}
var a = [0, 1, 2, 3];
map(function(x) { return x = x * x }, a);
console.log(a);
a:[0, 1, 4, 9]
但是,如果我将map(f, a)
更改为:
function map(f, a) {
for(var i in a) {
f(a[i]);
}
}
var a = [0, 1, 2, 3];
map(function(x) { return x = x * x }, a);
console.log(a);
a保持不变为:[0, 1, 2, 3]
我不确定这里发生了什么。似乎解释器将a[i]
视为对a
中对象map(f, a)
的属性的引用,但一旦传入f
,它就变成typeof number
。
答案 0 :(得分:1)
这是正确的行为,a[i]
的值被传递到f([i])
,而不是对它的引用,因此x
内部是明显的不同的变量/参考。
在第一个版本中你得到的结果仍然不同x
(函数返回)并将其分配到该数组位置......这是唯一的方法使用新的值来获取某些东西。
答案 1 :(得分:1)
不要在数组上使用for(... in...)
。使用for loop
。
for in
的枚举订单 NOT 保证。它还将遍历属性(不是内置的ins,而是由JS代码设置的东西)和原型上的东西,然后所有地狱都会松动。
接下来,除了数组和对象之外的所有值都是按值传递(基本上数组和对象也按值传递,但值是指向对象的指针)。
所以你不是在这种情况下修改数组中的值,而是局部变量x
恰好具有相同的值。
return x = x * x
这项任务是多余的。
修正版
function map(f, a) {
for(var i = 0, l = a.length; i < l; i++) {
a[i] = f(a[i]);
}
}
var a = [0, 1, 2, 3];
map(function(x) { return x * x }, a);
console.log(a);
答案 2 :(得分:0)
这个电话:
a[i] = f(a[i]);
实际上与此类似:
var arg = a[i];
var res = f(arg);
a[i] = res;
这称为“按值调用”,请参见此处:
答案 3 :(得分:0)
JavaScript中的数组是对象,而对象总是引用类型。
直到地图函数中存在a
的点,您已将其作为整个数组传递,这意味着您对a
所做的更改将在外部可见。
使用a[i]
取消引用数组后,您有一个Number
类型的变量,它不是引用类型。因此,匿名函数中对x
的更改不会传播回数组,只能在匿名函数本身中显示。