为了得到注释的输出,这段代码中一步一步地发生了什么?



userMsg = toUser("Bob")正在调用toUser("Bob")并将其分配给userMsg,然后将其与name连接并分配给greet。所以我的大脑想要看到greet = toUser("Bob") + name,这显然不是javascript在做的。userMsg = toUser("Bob");userMsg = message?或者是userMsg = toUser("Bob");

请帮助我理解。

function giveMessage(message) {

let userMsg = message;
userMsg = toUser("Bob");
return userMsg;
function toUser(userName) {
let name = userName;
let greet = userMsg + name;
return greet;
}

}
console.log(giveMessage("The world says hello dear: "));
// The world says hello dear: Bob

和这个一样吗?

function giveMessage(message) {

let userMsg = message;
let hello = toUser("Bob");
return hello;
function toUser(userName) {
let name = userName;
let greet = userMsg + name;
return greet;
}

}
console.log(giveMessage("The world says hello dear: "));
// The world says hello dear: Bob

这是第一个用行号注释的代码片段:

function giveMessage(message) {                          // line 1
// line 2
let userMsg = message;                                // line 3
userMsg = toUser("Bob");                             // line 4
return userMsg;                                      // line 5
function toUser(userName) {                          // line 6
let name = userName;                             // line 7
let greet = userMsg + name;                      // line 8
return greet;                                    // line 9
}                                                    // line 10
// line 11
}                                                        // line 12
console.log(giveMessage("The world says hello dear: ")); // line 13

函数giveMessage从第1行开始定义,但只有在第13行console.log()内部调用时才会调用。

当它被调用时,执行步骤的顺序是:

  1. 执行第3行(设置userMsgmessage的值,即"The world says hello dear: ")
  2. 开始执行第4行,通过计算赋值表达式的右侧(即调用函数toUser("Bob"))。
  3. 执行第7行(作为函数调用的一部分),并将name赋值为userName的传入值,即"Bob"
  4. 执行第8行,将greet设置为userMsgname的连接值。注意,userMsg仍然保留在步骤1中分配的值,因为我们仍然只计算第4行的右侧。这意味着greet被设置为"The world says hello dear: " + "Bob"
  5. 函数返回greet的值,我们跳转回第4行,完成在步骤2中开始的赋值。现在我们正在设置userMsg并覆盖之前在其中设置的值,但该值已经在步骤4中使用过,所以我们没有丢失任何东西。
  6. 返回userMsg的新值

第二个代码片段只是引入了一个新变量来保存对toUser(...)的调用的输出,并且对toUser(...)内部发生的事情没有影响。

@Ergwun已经发布了一个很好的答案。我想从另一个角度来看这个问题。你可以简单地"inline";通过将return替换为userMsg =来获得等效的函数。希望这有助于澄清你的疑问。

function giveMessage(message) {
let userMsg = message;
// userMsg = toUser("Bob");
// "inline" the `toUser` function:
{ 
let userName = "Bob"; // toUser(userName = "Bob")
let name = userName;
let greet = userMsg + name;
userMsg = greet;      // return greet;
}
return userMsg;
}
console.log(giveMessage("The world says hello dear: "));

最新更新