为什么我的闭包函数不想在 if 语句中重新分配其父函数变量?

Why doesn't my closure function want to reassign its parent function variable, when within an if statment?

我已经创建了这个用于描述游戏逻辑的工厂函数。我使用内部函数在游戏中切换玩家。问题是,当我尝试从内部函数中重新分配当前播放器时,它不起作用。当前玩家永远不会改变。我想这是我没有真正理解的关于关闭的东西。你能向我解释一下我错过了什么吗?这是我正在处理的代码:

const game = (() => {
    let player1 = "Jim";
    let player2 = "Mary";
    let currentPlayer = player1;

    const switchPlayers = () => { //This closure function is supposed to reassign the value of currentPlayer above. But it does not do it.
        if (currentPlayer === player1) {
            currentPlayer = player2;
        } else {
            currentPlayer = player1;
        }
        return currentPlayer;
    };

    return {currentPlayer, switchPlayers};

})();

game.switchPlayers // works as needed and switches the players every time it is invoked but does not reassign the variable within its parent function;
game.currentPlayer // does not get reassigned, when switchPlayers function is invoked, and returns player1 as was assigned at the start;

您需要获取一个对象引用并将玩家存储在内部,而不是外部,因为该对象不会改变状态。

const game = function() {
    let player1 = "Jim";
    let player2 = "Mary";
    let currentPlayer = player1;

    const
        switchPlayers = () => {
            object.currentPlayer = object.currentPlayer === player1 
                ? player2
                : player1;
            return object.currentPlayer;
        },
        object = { currentPlayer, switchPlayers };
    
    return object;
}();

console.log(game.switchPlayers());
console.log(game.currentPlayer);
console.log(game.switchPlayers());
console.log(game.currentPlayer);

您的代码 returns value of currentPlayer 不会在原始对象的 属性 更新时更新。因此,闭包工作正常,但事实是您的 returned 值没有指向更新的对象,它只是一个新值,在 return 语句时将保持不变。

您需要使用如下函数 return 值。

let game = (() => {
  let player1 = "Jim";
  let player2 = "Mary";
  let currentPlayer = player1;

  const switchPlayers = () => { //This closure function is supposed to reassign the value of currentPlayer above. But it does not do it.
    if (currentPlayer === player1) {
      currentPlayer = player2;
    } else {
      currentPlayer = player1;
    }
    return currentPlayer;
  };
  
  const getCurrentPlayer = () => currentPlayer;

  return {
    currentPlayer,
    switchPlayers,
    getCurrentPlayer
  };

})();

game.switchPlayers();
console.log(game.currentPlayer);
console.log(game.getCurrentPlayer());

OR 只需在函数的 this 指针上定义 属性 currentPlayer,然后将其用作类型(使用 new 关键字),如下所示。

function GameType() {
   let player1 = "Jim";
   let player2 = "Mary";
   this.currentPlayer = player1;

   this.switchPlayers = () => { //This closure function is supposed to reassign the value of currentPlayer above. But it does not do it.
     if (this.currentPlayer === player1) {
       this.currentPlayer = player2;
     } else {
       this.currentPlayer = player1;
     }
     return this.currentPlayer;
   };
 }

let game = new GameType();

console.log(game.currentPlayer);

game.switchPlayers();
console.log(game.currentPlayer);

重新分配变量。

问题是您 return 的对象具有这些变量的 副本的属性,而不是对变量的引用。

因此 let currentPlayer 已更改,但 game.currentPlayer 仍包含原始值的副本。

去掉变量,只修改对象属性。

const game = (function() {
  const player1 = "Jim";
  const player2 = "Mary";
  let o = {
    currentPlayer: player1
  };

  const switchPlayers = () => {
    if (o.currentPlayer === player1) {
      o.currentPlayer = player2;
    } else {
      o.currentPlayer = player1;
    }
    return o.currentPlayer;
  };

  o.switchPlayers = switchPlayers;
  return o;
})();

console.log(game.currentPlayer);
console.log(game.currentPlayer);
console.log(game.switchPlayers());
console.log(game.currentPlayer);
console.log(game.currentPlayer);