2012-10-10 148 views
2

我非常抱歉要求另一個匿名函數的問題,但它每當我找出它們時都會出現接縫,JavaScript會給我另一個曲線球。匿名函數包裝局部變量並返回新函數

我使用KineticJS創造了多個圓的動畫,然後他們像這樣(以下these tutorials

for (i = 0; i < rows; i++) 
{ 
    for (j = 0; j < cols; j++) 
    { 
     index = i * cols + j; 
     circles [ index ] = new Kinetic.Circle({...}); 
     ... 
    } 
} 
... 
for (i = 0; i < rows; i++) 
{ 
    for (j = 0; j < cols; j++) 
    { 
     index = i * cols + j; 
     anims [ index ] = new Kinetic.Animation({func: function (frame) 
      { 
       (function (innerCircle) 
       { 
        ... 
       } (circles [ index ])); 
      }, 
      node: layer 
     } 
    ); 
    } 
} 

我的目的是創建匿名函數時傳遞的index當前值。問題是隻有最後一張圖像被動畫,我不知道爲什麼。這裏是full jsfiddle

回答

3

你應該創建一個新的變量作用域的函數位於錯誤的地方。它應該在通過的功能之外,並且應該返回一個新功能。

返回的函數將有權訪問所需的值。

for (i = 0; i < rows; i++) 
{ 
    for (j = 0; j < cols; j++) 
    { 
     index = i * cols + j; 
     anims [ index ] = new Kinetic.Animation({func: function(innerCircle) { 
                 return function (frame) { 

                 }; 
                 })(circles[index]), 
      node: layer 
     } 
    ); 
    } 
} 

不過說實話,不喜歡這樣的內聯函數。當你創建一個返回你的函數的命名函數時,它變得非常清晰。

function makeFunc(innerCircle) { 
    return function (frame) { 
      // you can use innerCircle in here 
    }; 
} 

for (i = 0; i < rows; i++) { 
    for (j = 0; j < cols; j++) { 
     index = i * cols + j; 
     anims [ index ] = new Kinetic.Animation({ 
     func: makeFunc(circles[index]), 
     node: layer 
     }); 
    } 
} 

有些人只是因爲某些原因喜歡這些內聯函數,但我認爲他們只是增加了混亂。一個命名函數將代碼分解一點,並向代碼添加一些文檔。

此外,它的效率稍高一點,因爲在循環的每次迭代中都沒有創建新的內聯函數。相反,您正在重複使用同一個構建處理程序。

+0

感謝您的解決方案,並建議 – puk

+0

不客氣。 –

+2

+1。在for循環中使用它們時會分解函數通常是更好的做法(由於關閉和可讀性) –