2011-06-22 16 views
34

मुझे वास्तव में बैकबोन पसंद है, लेकिन मुझे सबसे कठिन समय लगता है जो सरल चीजें प्रतीत होता है। मैं निम्नलिखित उदाहरण के साथ किसी भी मदद की सराहना करता हूं।Backbone.js Arrays

मेरे पास एक मॉडल है, मानदंड, कि मैं अपने यूआई में कुछ वस्तुओं की स्थिति को स्टोर करने के लिए उपयोग करना चाहता हूं। कुछ सरल विशेषताएं हैं, और एक विशेषता जो यूआई में चुने गए टैग की आईडी स्टोर करने के लिए उपयोग की जाने वाली आईडी की एक सरणी है।

तो, मैं एक नया उदाहरण बना देता हूं। मैं टैग सरणी में कुछ आइटम जोड़ता हूं। फिर, मैं ताजा शुरू करना चाहता हूं, एक नया उदाहरण बनाएं, जो एक ही चर को सौंपा गया हो। लेकिन, मेरे टैग सरणी को मानदंड के पहले उदाहरण के हिस्से के रूप में इसमें शामिल जानकारी रखने के लिए जारी है।

मैंने नीचे परीक्षण केस दस्तावेज किया है।

<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN" "http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd"> 
<html xmlns="http://www.w3.org/1999/xhtml"> 
<head> 
    <title>Test</title> 
    <script src="Scripts/Libraries/jquery-1.6.1.js" type="text/javascript"></script> 
    <script src="Scripts/Libraries/underscore.js" type="text/javascript"></script> 
    <script src="Scripts/Libraries/backbone.js" type="text/javascript"></script> 

    <script language="javascript" type="text/javascript"> 

     $(function() { 

      // Simple model to hold some state about my UI. 
      var Criteria = Backbone.Model.extend({ 

       defaults: { 
        "status": "Normal", 
        "priority": "Normal", 
        "tags": new Array() 
       } 

      }); 

      // Create new criteria. 
      window.criteria = new Criteria(); 

      // The length of the tags array should be 0. PASSES 
      console.log("Expect 0: Actual " + window.criteria.get("tags").length); 

      // Add a tag id to the tags array. 
      window.criteria.get("tags").push(5); // Tag with ID of 5. 

      // The length of the tags array should be 1. PASSES 
      console.log("Expect 1: Actual " + window.criteria.get("tags").length); 

      // Create a new instance of criteria. 
      window.criteria = new Criteria(); 

      // The length of the tags array should be 0. FAILS 
      // CONFUSED. I thought this is now a new instance with a new set of attributes. 
      // Why does the tags collection still have an item in it. 
      console.log("Expect 0: Actual " + window.criteria.get("tags").length); 

      // OK. So, I will call the clear method on the model. This is supposed to remove all attributes 
      // from the model. 
      // Then, I will create it again. 
      window.criteria.clear(); 
      window.criteria = new Criteria(); 

      // The length of the tags array should be 0. FAILS. Still 1. 
      console.log("Expect 0: Actual " + window.criteria.get("tags").length); 

      // ARGH! 
      console.log("HELP!"); 

     }); 

    </script> 

</head> 
<body> 
    <h1>Test</h1> 
    <p>Backbone test page.</p> 
</body> 
</html> 

क्या मैं यहां चिह्न से बाहर निकल गया हूं? क्या मैं उन चीजों के लिए बैकबोन का उपयोग करने की कोशिश कर रहा हूं जिसका इरादा नहीं था? या क्या मैं जावास्क्रिप्ट ओओ प्रोग्रामिंग में कुछ और सामान्य याद कर रहा हूं?

पीएस मैंने मूल रूप से टैग के बैकबोन संग्रह का उपयोग किया, लेकिन इसने कई संग्रहों में संदर्भित टैग मॉडल से संबंधित मुद्दों का एक अलग अलग सेट प्रस्तुत किया और बैकबोन की निकासी विधि किसी संग्रह से किसी आइटम को हटाए जाने पर "संग्रह" संदर्भ को कैसे सेट करता है। एक और दिन, एक और मुद्दा।

+0

हाय केविन, शायद आप नीचे दिए गए एक को अपना स्वीकृत उत्तर बदल सकते हैं? जो कहीं अधिक सुगम और अनुशंसित दृष्टिकोण है। स्वीकृत उत्तर वैसे भी वही चीज़ का एक फुलाया विचार है। धन्यवाद। – SuperDuperApps

उत्तर

34

थॉम ब्लेक कारण है कि यह के लिए एक ही मान रख रहा है के बारे में सही है:

बल्कि टैग के लिए एक डिफ़ॉल्ट मान सेट की तुलना में, तुम बस [] के लिए सेट करने के लिए इससे पहले कि आप पहली बार उपयोग करने में सक्षम होना चाहिए सरणी इसे हल करने के लिए एक विकल्प प्रारंभकर्ता में डिफ़ॉल्ट मान

 var Criteria = Backbone.Model.extend({ 

      defaults: { 
       "status": "Normal", 
       "priority": "Normal" 
      }, 

      initialize: function(){ 
       if(!this.get('tags')){ 
       this.set({tags: new Array()}); 
       } 
      } 

     }); 
+8

+1 इसे संभालने का बैकबोन तरीका दिखाने के लिए। –

+0

धन्यवाद। मैं इस दृष्टिकोण के बाद समाप्त हो गया और अब यह सही समझ में आता है। तो, बस यह सुनिश्चित करने के लिए, आदिम मान (स्थिति, प्राथमिकता) टैग सरणी की तरह रीसेट करने की आवश्यकता नहीं है? सही बात? – Kevin

+0

@ केविन सही। –

13

जब आप 'डिफ़ॉल्ट' के तहत 'टैग' को परिभाषित करते हैं, तो आप एक नया ऐरे बनाते हैं और उस वर्ग के डिफ़ॉल्ट मान पर सेट करते हैं। फिर, जब आप एक नया उदाहरण बनाते हैं, तो उसके पास एक ही ऐरे संदर्भ होता है, जिसमें अभी भी चीजें हैं जिन्हें आपने धक्का दिया है।

window.criteria = new Criteria() 
window.criteria.set({'tags', []}) //you can use new Array() if you want 
window.criteria.get('tags').push(5) 

window.criteria = new Criteria() 
console.log(window.criteria.get('tags')) //should be undefined 
window.criteria.set({'tags', []}) 
+2

मुझे जेएस डेट ऑब्जेक्ट्स को बैकबोन में गुणों के रूप में संग्रहीत करते समय हाल ही में एक ही समस्या थी। मॉडल प्रकार कक्षाएं।मैं सिर्फ एक संदर्भ को बदलकर नई तारीख वस्तुओं को नहीं बना रहा था। तो जहां तक ​​रीढ़ की हड्डी का सवाल था, तिथि कभी नहीं बदली और घटनाओं को कभी नहीं निकाल दिया गया। रूढ़िवादी रीढ़ की हड्डी के साथ नियम हमेशा अपरिवर्तनीय मूल्य के रूप में व्यवहार करते हैं। यदि आपको एक संपत्ति क्लोन को एक नया मान बदलने की आवश्यकता है जो एक नया संदर्भ बनाएगा और नया संदर्भ बदल देगा। – bradgonesurfing

+0

मैं आगे बढ़ गया और नीचे प्रारंभिक दृष्टिकोण का पालन किया। अच्छे खर्च। धन्यवाद! – Kevin

70

"डिफ़ॉल्ट" भी एक कार्य हो सकता है।

var Criteria = Backbone.Model.extend({ 
    defaults: function() { 
     return { 
      "status": "Normal", 
      "priority": "Normal", 
      "tags": new Array() 
     } 
    } 
}); 

यह एक नया मानदंड तत्काल होने पर एक नई सरणी बना देगा। देखें: http://backbonejs.org/#Model-defaults

+0

वापसी का उद्देश्य क्या है? – Tjorriemorrie

+10

कुंजी यह है कि "डिफ़ॉल्ट" संपत्ति किसी ऑब्जेक्ट की बजाय अब एक फ़ंक्शन है। रिटर्न फ़ंक्शन से लौटाई गई ऑब्जेक्ट को इंगित करता है और "डिफ़ॉल्ट" के मान के रूप में उपयोग किया जाता है। जैसा कि अन्य ने समझाया है, यदि "डिफ़ॉल्ट" एक वस्तु है, जब कोई नया मॉडल बनाया जाता है, तो "डिफ़ॉल्ट" में प्रत्येक प्रॉपर्टी को ऑब्जेक्ट के गुणों में कॉपी किया जाता है। जब गुण स्ट्रिंग्स या नंबर होते हैं, तो यह अपेक्षित काम करता है, लेकिन ऑब्जेक्ट्स और Arrays के लिए, यह प्रति संदर्भ द्वारा किया जाता है। प्रत्येक उदाहरण के लिए डिफ़ॉल्ट विशेषताओं की अपनी प्रतिलिपि बनाने के लिए, आपको एक फ़ंक्शन का उपयोग करना चाहिए। – btford

+7

मैं चुने हुए उत्तर – Pablote

3

स्पष्ट होने के लिए, मैक्सिम एच द्वारा प्रदान किया गया अंतिम विकल्प समस्या का समाधान नहीं करेगा। डिफ़ॉल्ट संपत्ति मान ली जाती है कि सभी मान सेट अपरिवर्तनीय हैं। हालांकि, एक सरणी उत्परिवर्तनीय है, जिसका अर्थ है कि इसका मूल्य बदला जा सकता है (उदा। टैग [0] = "हैलो" टैग [0] = "हाय वहाँ" के साथ बदला जा सकता है)।

बीटीफ़ोर्ड के उत्तर का उपयोग करके, आप मॉडल के हर नए उदाहरण पर किसी भी उत्परिवर्तनीय वस्तु/संपत्ति का निर्माण करने के लिए एक नया उदाहरण तैयार कर रहे हैं, इसलिए इसे कभी साझा नहीं किया जाता है, क्योंकि ऑब्जेक्ट फ़ंक्शन स्कोप्ड चर के साथ बनाया जाता है।

इसी तरह, डेरिक बेली का जवाब सही है, यह केवल डिफ़ॉल्ट विधि के बजाय प्रारंभिक विधि का उपयोग करता है।