2011-05-10 13 views
10

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

उदाहरण के लिए:

class List extends Array 
    # Some other stuff to make it work... 

list = new List(1,2,3) 

console.log list 
 
[1, 2, 3] 
+0

नहीं यह दो अलग में इस सवाल को विभाजित करने के अच्छा नहीं होगा; सुपर के लिए कन्स्ट्रक्टर तर्कों के सामान्य उत्तीर्ण होने के लिए पहला, दूसरा 'अरे' के अजीब व्यवहार के बारे में दूसरा? – Mitja

उत्तर

8
class List extends Array 
    constructor: -> 
     @push arguments... 

    toString: -> 
     @join('-') 

list = new List(1, 2) 

list.push(3) 

list.toString() 

=>

 
'1-2-3' 
+0

माता-पिता ऑब्जेक्ट के कन्स्ट्रक्टर को सभी तर्कों को पारित करने का एक सामान्य तरीका होना अच्छा होगा, लेकिन यह इस मामले के लिए नौकरी करता है :) – Acorn

+1

क्योंकि ऐरे में 'कन्स्ट्रक्टर' विधि नहीं है, लेकिन यह संभव नहीं है .. लेकिन हाँ , ये अच्छा होगा। =) – jejacks0n

+0

यह सख्त मोड में काम नहीं करता है, क्योंकि उस मामले में "तर्क" मौजूद नहीं है। – monokrome

24

सामान्य रूप से, यह अतिरिक्त कोड के बिना काम करेगा; माता-पिता निर्माता जब तक स्पष्ट अधिरोहित प्रयोग किया जाता है:

class A 
    constructor: -> 
    console.log arg for arg in arguments 

class B extends A 

new B('foo') # output: 'foo' 

और समस्या नहीं है कि सरणी एक constructor विधि नहीं है:

coffee> Array.constructor 
[Function: Function] 

समस्या सिर्फ इतना है कि Array है सिर्फ सादा अजीब है। जबकि सरणी सिद्धांत रूप में "केवल वस्तुएं" हैं, अभ्यास में वे अलग-अलग संग्रहित होते हैं। तो जब आप उस कन्स्ट्रक्टर को उस ऑब्जेक्ट पर लागू करने का प्रयास करते हैं जो एक सरणी नहीं है (भले ही यह instanceof Array परीक्षण पास हो), यह काम नहीं करता है।

तो, आप एकोर्न के समाधान का उपयोग कर सकते हैं, लेकिन फिर आप सड़क के नीचे अन्य समस्याओं में भाग ले सकते हैं (विशेष रूप से यदि आप List को किसी वास्तविक सरणी की अपेक्षा करते हैं)। इसी कारण से, मैं एक देशी ऑब्जेक्ट प्रकार से विरासत का उपयोग करने की कोशिश करने के बजाय, एक सरणी उदाहरण के चारों ओर एक रैपर के रूप में List को लागू करने की अनुशंसा करता हूं।

हम विषय पर हैं, तब एक बहुत महत्वपूर्ण स्पष्टीकरण: यदि आप अपने आप में super उपयोग करते हैं, कि सभी तर्कों पास करता है! यह व्यवहार रुबी से उधार लिया जाता है। तो

class B extends A 
    constructor: -> 
    super 

', रों निर्माता जबकि

class B extends A 
    constructor: -> 
    super() 

A लागू करेगा' A के सभी तर्कों साथ भेज देते हैं कोई तर्क के साथ रों निर्माता होंगे।

+0

शानदार स्पष्टीकरण के लिए धन्यवाद! '" मैं सरणी उदाहरण के चारों ओर एक रैपर के रूप में सूची को कार्यान्वित करने की अनुशंसा करता हूं "'आप यह करने के बारे में कैसे जाएंगे? यदि आपके पास समय है तो एक छोटा सा उदाहरण बहुत सराहना की जाएगी! – Acorn

+0

खैर, मेरा मतलब यह है कि कन्स्ट्रक्टर कुछ @ @arr = Array :: slice.call तर्क, 0 '(किसी ऑब्जेक्ट में तर्क विधि को परिवर्तित करने की मानक विधि) जैसा दिखता है, तो आप प्रत्येक सरणी विधियों को लागू करेंगे सरल पास-थ्रू के रूप में (जैसे 'पुश: -> @ arr.push.apply arr, arguments', 'toString: -> @ arr.toString()', ...), और फिर अंत में अपनी' सूची 'जोड़ें तरीकों। –

+0

ओह वाह, प्रत्येक विधि के माध्यम से व्यक्तिगत रूप से गुजर रहा है .. यह थोड़ा कठिन लगता है :) – Acorn

-1

जावास्क्रिप्ट की मेरी खोज में मुझे एक रचनात्मक तर्कों की एक गतिशील संख्या के साथ कक्षा बनाने के लिए एक सामान्य तरीका चाहिए। जैसा कि बताया गया है कि यह सरणी के लिए काम नहीं करेगा, जहां तक ​​मुझे पता है, यह केवल कॉफी-स्क्रिप्ट शैली कक्षाओं के लिए काम करेगा।

तर्कों की एक गतिशील संख्या के साथ एक विशेष समारोह कॉलिंग एक वर्ग एक चर में सहेजा विस्तार कर सकते हैं के माध्यम से .apply

args = [1, 2, 3] 
f = measurement.clone 

f.apply measurement, args 

एक वर्ग काफी आसान है। नतीजतन हम एक ऐसा कार्य लिख सकते हैं जो नए उप-वर्गों को लौटाता है।

classfactory = (f) -> 
    class extension extends f 

यह सब एक साथ लाना हम एक समारोह है कि नए उप-वर्गों रिटर्न बना सकते हैं जो सुपर वर्ग के निर्माता के लिए हम apply बहस में।

classwitharguments = (f, args) -> 
    class extension extends f 
     constructor:() -> 
      extension.__super__.constructor.apply @, args 

इस नए कारखाने

args = [1, 2, 3] 
instance = new (classwitharguments Measurement, args) 

विचार का उपयोग करने के लिए? टिप्पणियाँ? सुझाव? सीमाएं मैंने नहीं सोचा था? मुझे बताएं।

2

कॉफीस्क्रिप्ट में extends का उपयोग करके सुपरक्लास कॉफीस्क्रिप्ट में भी होने की उम्मीद करता है। यदि आप एक गैर-सीएस वर्ग का उपयोग कर रहे हैं, उदा। मूल प्रश्न में Array, तो आपको समस्याएं आ सकती हैं।

इससे मेरे लिए सामान्य मामला हल हो गया। यह एक हैक का थोड़ा सा है क्योंकि यह _super का उपयोग करता है जो शायद संकलित जेएस में उपयोग करने का इरादा नहीं है।

class MyClass extends SomeJsLib 

    constructor: -> 
    _super.call @, arg1, arg2 

या आप बस फोन करने वाले से बहस के माध्यम से पारित करने के लिए चाहते हैं:

class MyClass extends SomeJsLib 

    constructor: -> 
    _super.apply @, arguments 
संबंधित मुद्दे