2009-12-11 21 views
29

मैं कैनवास टैग के साथ जावास्क्रिप्ट गेम बना रहा हूं, और मैं प्लेयर की स्थिति अपडेट करने के लिए लूप के लिए एक उन्नत का उपयोग कर रहा हूं।जावास्क्रिप्ट में अजीब व्यवहार ... लूप

संक्षेप में:

var actors = new Array(); 

var player = new Actor(0, 0, img); 

actors[0] = player; 

function update_positions() { 
    //position 1 
    for(var a in actors) { 
     //position2 
     a.xpos += a.xvel; 
     a.ypos += a.yvel; 
    } 
} 

बस के बाहर की स्थिति 1 पर पाश के लिए, मैं के अभिनेताओं [0] .xvel सही मान पहुँच सकते हैं। स्थिति 2 पर लूप के अंदर, a.xvel अपरिभाषित है। क्या कोई मुझे बता सकता है कि क्या हो रहा है?

+1

कृपया यह प्रश्न भी देखें http://stackoverflow.com/questions/1886179/why-does-javascript-turn-array-indexes-into-strings-when-iterating/1886259#1886259 – pramodc84

+3

[के लिए उपयोग न करें सभी में सरणी के लिए-लूप] (http://stackoverflow.com/q/500504/1048572) – Bergi

उत्तर

79

for...in बयान का मतलब है, से अधिक वस्तु गुण पुनरावृत्ति करने के लिए इस्तेमाल किया जा करने के लिए अपने कोड देख कर लगता है कि actors एक सरणी (आप सूचकांक 0 के साथ प्रारंभिक तत्व सेट कर रहे हैं) है।

यह कथन crawl up प्रोटोटाइप श्रृंखला भी होगा, यदि आपने Array.prototype बढ़ाया है तो उन गुणों को फिर से चालू किया जाएगा, और पुनरावृत्ति का क्रम भी जरूरी नहीं है।

मैं problems से बचने और पाश के लिए एक सामान्य का उपयोग कर पुनरावृति करने के लिए आप की सिफारिश करेंगे:

for (var i = 0; i < actors.length; i++) { 
    actors[i].xpos += actor.xvel; 
    actors[i].ypos += actor.yvel; 
} 

अगर मैं गलत हूँ, और actors किसी सरणी नहीं है, मैं hasOwnProperty विधि का उपयोग करने की सलाह देंगे, करने के लिए यह सुनिश्चित करें कि संपत्ति नहीं कहीं प्रोटोटाइप श्रृंखला में वस्तु अपने आप में मौजूद है,:

for (var name in object) { 
    if (object.hasOwnProperty(name)) { 
    // 
    } 
} 
+9

+1 जो मैं टाइप कर रहा था :-) वास्तव में, वास्तव में ** सरणी पर ** 'के लिए ...' का उपयोग न करें। – bobince

+24

भगवान! सभी वेब तकनीक पूरी तरह से counterintuitive लगता है। धन्यवाद – Maleev

2

a.xpos के बजाय actors[a].xpos का उपयोग करने का प्रयास करें।

JavaScript for-in loops पर अधिक जानकारी के लिए यहां देखें।

4

ऐसा लगता है कि आप नाम पर ऑब्जेक्ट गुणों तक पहुंचने का प्रयास कर रहे हैं, यहां मूल्य नहीं। इंडेक्स, इस मामले में '0', को/इन लूप में 'ए' को असाइन किया जाता है।

जो आप करना चाहते हैं वह सरणी सदस्य के मूल्य तक पहुंच है, यानी: अभिनेता [ए]। एक सरणी के सूचक, नहीं अपने सदस्यों के माध्यम से

for(var a in actors) { // a=0 the first time around the loop, 
    actor = actors[a]; // same thing as actors[0]; 
    actor.xpos += actor.xvel; 
    actor.ypos += actor.yvel; 
} 
+0

धन्यवाद।मैं खुद को भ्रमित करने से रोकने के लिए अब से लाइवस्क्रिप्ट को कॉल करना शुरू कर रहा हूं। – Spencer

2

for (x in y) निर्माण दोहराता:

इस प्रयास करें।

0

एक अन्य विकल्प underscore लाइब्रेरी का उपयोग करने के लिए है:

_.each(actors, function(a) { 
    a.xpos += a.xvel; 
    a.ypos += a.yvel; 
}); 

या आप अंडरस्कोर का उपयोग नहीं करना चाहते हैं, लेकिन वैसे भी JQuery उपयोग कर रहे हैं, तो आप कर सकते हैं:

$.each(actors, function(i, a) { 
    a.xpos += a.xvel; 
    a.ypos += a.yvel; 
}); 

एक यात्रा के इस कार्यात्मक पैटर्न की अच्छी सुविधा है जो आपको करने के लिए var का उपयोग कर सकते है लूप में वेरिएबल्स घोषित करें जो लूप के शरीर में डूबे हुए हैं, जो जावास्क्रिप्ट के विषम चर स्कॉइंग नियमों से काटने से बचने में मदद करता है।

संबंधित मुद्दे