函数范围内外的数组之间的范围泄漏?

时间:2015-07-09 23:26:33

标签: javascript node.js

我在我的脚本main

中调用了一个函数
function func(a) {
var idx;
a=a.sort();  

for (idx = 0; idx < a.length + 1; idx += 1) {
    if (a.indexOf(idx) === -1) {
        return idx;
    }
}
return 0;
}

var array = [2,1,0];
var b = func(array);
console.log(array);

函数参数(a)是一个传递给func函数的数组。

当我在调用此函数后尝试访问程序主体中的数组时,它已经排序了。

node.js是否链接了传递给'func'函数的数组和传递给它的数组之间的范围?

调用此代码后,数组已排序。那是为什么?

如果我在函数范围内声明一个新变量b,这甚至是正确的。

function func(a) {
var idx, b;
b = a;  
b = b.sort();

for (idx = 0; idx < a.length + 1; idx += 1) {
    if (a.indexOf(idx) === -1) {
        return idx;
    }
}
return 0;
}

var array = [2,1,0];
var b = func(array);
console.log(array);

上面的代码有同样的问题。

1 个答案:

答案 0 :(得分:2)

这不是范围泄漏,而是发生了什么的双重原因:

  1. 因为sort直接修改了应用它的数组(同时也返回它)
  2. JavaScript中的函数使用对象的引用传递
  3. 为了理由#1,请看这个简单的例子:

    var a = [3,4,1,2];
    a; // [3, 4, 1, 2]
    a.sort(); // [1, 2, 3, 4]
    a; // [1, 2, 3, 4]
    

    正如您所看到的那样,它返回的排序数组只不过是由sort修改过的数组本身。

    理由#2看一下这个简单的例子:

    function foo(a) { a.push('hello'); }
    var arr = [1,2,3,4];
    arr; // [1, 2, 3, 4]
    foo(arr); // undefined
    arr; // [1, 2, 3, 4, "hello"]
    

    因此,结合这两个原因,您可以看到您将对数组的引用传递给函数,然后使用sort直接修改它。

    如果你想在不修改原始数组的情况下做同样的事情,可以使用Array.prototype.slice()返回原始数组的浅表副本。

    var a = [3,4,1,2];
    var arr = a.slice();
    a; // [3, 4, 1, 2]
    arr; // [3, 4, 1, 2]
    arr.sort(); // [1, 2, 3, 4]
    arr; // [1, 2, 3, 4]
    a; // [3, 4, 1, 2]