回调函数是否在javascript中创建了一个新的作用域?

Does the callback function create a new scope in javascript

本文关键字:一个 作用域 是否 函数 javascript 创建 回调      更新时间:2023-09-26
function hello() {
  var result = [];
  var str = 'I am here';
   function inner() {
    var result = [];
     for (var i=0;i<10;i++) {
        result.push(i);
     }
     return result;
   }
}

在上面的代码中,当我调用函数hello()时,返回值是一个空的[],也没有console.log内部函数的str。但是,在下面的代码集中,我使用了一个回调函数:

 function forEach(cb) {
   for(var i =0;i<10;i++) {
    cb(i);
   }
}
function hello() {
   var result = [];
   var str = 'I am here';
   forEach(function(num) {
    console.log(str);
     result.push(num);
   }); 
   return result;
}

的问题是为什么两个函数反应,并给出不同的输出?请注意;在这两个代码中都有一个内部函数,它应该创建一个可以访问外部作用域的新作用域?有人对这个问题有好的解释吗?由于

在第一个代码块中,inner是一个在hello内部声明的新函数。它不会执行,因为您没有调用它。当它被调用时,它确实在hello内部创建了一个新的子作用域。但是,由于hello()实际上不返回任何东西并且不调用inner(),所以当您调用hello()时,您将获得undefined。您可以通过这样修改来修复这个问题(您可以运行这个代码片段来查看返回值):

function hello() {
    var str = 'I am here';
    // declare inner
    function inner() {
        var result = [];
        for (var i = 0; i < 10; i++) {
            result.push(i);
        }
        return result;
    }
    // now call inner() and return its result
    return inner();
}
console.log(hello());

在其他函数内部声明的函数会创建一个新的作用域。Javascript中的每个函数声明和相应的调用都会创建一个新的作用域。如果函数位于另一个函数内部,则该内部函数中的代码可以访问其局部作用域和父作用域,并且可以嵌套到嵌套函数声明的最深处。

的问题是为什么两个函数反应,并给出不同的输出?请注意;在这两种密码中都有一个内部功能创建一个可以访问外部作用域的新作用域?有人对这个问题有很好的解释吗?由于

在第一个例子中,你从来没有调用过内部函数,所以它从来没有执行过。


在第二个示例中,将内联匿名函数引用作为函数参数传递给forEach()函数。当forEach()函数执行时,它用cb(i)代码行调用回调函数,这就是第二个例子中调用回调函数的方式。forEach()为您呼叫。

同样,在第二个示例中,局部声明的回调函数正在访问父作用域并修改result数组(这是完全允许的)。在第一个代码示例中,在inner函数作用域中声明了一个新的result变量,然后返回该变量。您没有访问父result变量。当你声明一个与父变量同名的局部变量时,该局部变量将覆盖父变量(实际上隐藏了父变量),并且在局部作用域中对该变量的任何引用都只能访问该局部变量。

您可以像这样编写第一个代码示例来使用父作用域result变量:

function hello() {
    var result = [];
    var str = 'I am here';
    // declare inner
    function inner() {
        for (var i = 0; i < 10; i++) {
            result.push(i);
        }
        return result;
    }
    // now call inner() and return result
    inner();
    return result;
}
console.log(hello());

您混淆了函数声明和函数调用。

可以用多种方式声明函数:

function myNewFunction() {}

现在这个函数存在于当前作用域中,但是除非被调用,否则不会执行。

你可以像这样调用函数。现在你的函数将被执行。

myNewFunction();

函数及其作用域可以与变量进行比较。在另一个函数中定义的函数只能从父函数中访问。让我给你举个例子。

    function myMegaFunction() {
        console.log("in mega");
        function mySmallFunction() {
            console.log("in small");
        }
    }
    myMegaFunction(); 

这将只打印- 'in mega'。如果你在myMegaFunction里面调用mySmallFunction(),那么这两行都将被打印。


现在让我们看一个更复杂的场景:

    function myMegaFunction() {
        console.log("in mega");
        var str = "car";
        var result = function mySmallFunction() {
            console.log("in a small", str);
        }
        return result;
    }
        
    var resultingFunction = myMegaFunction();
    resultingFunction();

这将首先打印以下内容:in megain a small car

本质上,这是函数像变量一样传递。它们也可以稍后执行。