簡體   English   中英

Javascript:如何在函數內修改全局變量?

[英]Javascript: How to modify global variables within functions?

以下是我正在處理的代碼。 我想知道為什么,當我更改函數中的變量ttt時,更改不會停留在函數之外? 我已將其聲明為var ttt = new Array; 在最頂端。

另外,為什么我不能在函數中使用變量i

碼:

  client.on('connection', function()
    {
        var sss;
        var aaa;

            console.log('Connected');

        for (i = 0 ; i < 120 ; i++)
            ttt[i] = 0;

        for (i = 0 ; i < 9 ; i++)
        {
                client.getMatchHistory(434582, function(err, result)        
            {
                sss = JSON.stringify(result);
                var myObject = eval('(' + sss + ')');
                console.log (myObject.object.data[i].object.value);

                ttt[myObject.object.data[i].object.value]++;
            });

        }

            for (i = 0 ; i < 120 ; i++)
                console.log ("Record" + i + " Successes: " + ttt[i]);

    });

正如您所指出的,您的代碼存在兩個獨立的問題,並且它們都有些相關。 首先, ttt 正在全球范圍內進行修改。 問題是你在修改之前檢查它們。 我懷疑client.getMatchHistory()正在進行異步調用。 無法保證第二個for循環中的所有異步操作都將在執行第三個for循環時執行,在第三個for循環中讀取數組。

第二個問題是范圍問題,但問題不在於全球范圍。 由於client.getMatchHistory()是異步的,因此一旦循環執行完畢,就會調用回調。 循環完成后, i的值為10 可能這不是你想要的。 您需要創建一個回調生成函數,它接受i的值,並返回一個可用作回調的函數。 像這樣:

function make_callback(i) {
  return function(err, result) {
    // The body of your callback in here
  };
}

然后你應該在循環體中使用它:

client.getMatchHistory(434582, make_callback(i))

這將捕獲當前迭代中i的值,生成的回調將在執行時使用該值。 這應該解決您的問題i

首先,所有全局變量都是有效的“窗口”對象字段,因此您可以使用window.ttt來確保使用全局變量而不是本地變量。 這段代碼應該有效,你是否在開發人員工具中嘗試過? 調試器對這種變量的存在有何看法?

至於變量i:當然,你可以使用它,但最好在本地使用它,定義'var i;' 在函數的頂部不破壞全局命名空間。

client.getMatchHistory可能是異步請求,你希望在循環之后,你將填充ttt數組,為了實現這一點,你必須創建一個在最后一個循環步驟之后運行的處理程序:

var afterloop=function() {
    for (var i = 0 ; i < 120 ; i++)
       console.log ("Record" + i + " Successes: " + ttt[i]);
}
for (var i = 0 ; i < 120 ; i++)
        ttt[i] = 0;

var i_final=0;
for (var i = 0 ; i < 9 ; i++)
        {   
            var i=i;   //localise i
            client.getMatchHistory(434582, function(err, result)        
            {
                i_final++;
                sss = JSON.stringify(result);
                var myObject = eval('(' + sss + ')');
                console.log (myObject.object.data[i].object.value);

                ttt[myObject.object.data[i].object.value]++;
                if (i_final>8) {afterloop();}
            });

        }

在示例中, i_final計數完成請求,它們可以按隨機順序完成,由於異步,所以在決定運行afterloop()時,你不能引用i ,當i_final計數到超過上次執行的請求時,你運行函數應在最后一次請求完成后執行。

注意: 請盡可能少地使用全局變量,在您使用全局i代碼中沒有任何理由

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM