2012-06-08 108 views
11

如何保持對我的for循環中的i變量的訪問?我試圖學習,不只是得到答案,所以一些解釋會非常有幫助。謝謝!Javascript可變範圍內循環

var el, 
    len = statesPolyStrings.length; 

for (var i = 0; i < len; i++) { 
    el = document.getElementById(statesPolyStrings[i]); 

    google.maps.event.addDomListener(el, 'mouseover', function() { 
     $("#"+statesPolyStrings[i]).addClass("highlight"); 
     statesPolyObjects[i].setOptions({ strokeWeight: '2' }); 
    }); 
} 
+1

你想在for循環之外訪問'i'嗎?您已經可以訪問for循環中的'i'。 –

+0

我想在for循環中的函數addDomListener中訪問它。無論你在上面的代碼中看到我,我都希望使用i,並在for循環中增加。 –

+1

可能重複[Javascript閉合內部循環 - 簡單實用的例子](http://stackoverflow.com/questions/750486/javascript-closure-inside-loops-simple-practical-example) –

回答

28

所有的回調共享相同的i變量。
當事件處理程序實際運行時,i在數組結尾之後。

您需要將循環體包裝在一個自調用函數中,該函數以i作爲參數。
這樣,每次迭代都會得到它自己的,不變的,i變量。

例如:

for (var i = 0; i < statesPolyStrings.length; i++) { 
    (function(i) { 
     ... 
    })(i); 
} 
+0

你能提供一個例子,通過更正我的碼?我不確定你是什麼意思。 –

+0

明白了,現在明白了。謝謝。 –

1
for (var i = 0; i < statesPolyStrings.length; i++) { 
    (function(i){ 
     google.maps.event.addDomListener(document.getElementById(statesPolyStrings[i]), 'mouseover', function() { 
     $("#"+statesPolyStrings[i]).addClass("highlight"); 
     statesPolyObjects[i].setOptions({ strokeWeight: '2' }); 
     }); 
    })(i) 
} 
2

與自我調用函數的訣竅正常工作:它創建了一個新的領域(也許谷歌的「範圍,功能的JavaScript」),因此處理i的不同變量並將正確的值傳遞給您的事件偵聽器回調函數。

但你其實並不需要使用jQuery再次找到你的元素因爲你已經分配了一個事件偵聽器,它和你的函數裏面你有this參考,你的元素。

正如你使用jQuery無論如何,它是那麼容易找到正確的索引(您i)的statesPolyObjects$.inArray()通過你的元素的ID和statesPolyStrings陣列(假設你正在處理的唯一的ID。如果不是,$("#"+statesPolyStrings[i])也會失敗,因爲它首先找到它)。

var el; 

for (var i = 0, len = statesPolyStrings.length; i < len; i++) { 
    el = document.getElementById(statesPolyStrings[i]); 

    google.maps.event.addDomListener(el, 'mouseover', function(event) { 
     $(this).addClass("highlight"); 
     statesPolyObjects[$.inArray(this.id, statesPolyStrings)]. 
      setOptions({ strokeWeight: '2' }); 
    }); 
} 

如果你仍然想用自調用函數來堅持,你應該改變,無論如何以下行:

("#"+statesPolyStrings[i]).addClass("highlight"); 

$(this).addClass("highlight"); 

如果你不熟悉不夠用this以及您可能想要閱讀此文章的活動: http://www.sitepoint.com/javascript-this-event-handlers/

您可能已經注意到我也在匿名回調函數中寫了參數event。嘗試console.log這個事件,您可以免費獲得任何事件偵聽器回調函數,並探索您可以訪問的所有其他事物。例如,你可以用event.target找到你點擊的實際元素(因爲實際的鼠標懸停可能發生在你的元素的子元素上)。所以:

google.maps.event.addDomListener(el, 'mouseover', function(event) { 
    console.log(event); 
    ... 

並打開您的瀏覽器的控制檯,以查看事件交付...

請注意,雖然google.maps.event.addDomListener通過了不同的東西,然後document.body.addEventListener,瀏覽器之間也有所不同。例如jQuery.on()也在事件對象中提供了一些不同的東西,但在那裏你至少可以指望所有瀏覽器中的相同數據。