यह एक बहुत ही सरल प्रोटोटाइप आधारित ऑब्जेक्ट मॉडल है जिसे स्पष्टीकरण के दौरान एक नमूना माना जाएगा, जिसमें अभी तक कोई टिप्पणी नहीं है:
function Person(name){
this.name = name;
}
Person.prototype.getName = function(){
console.log(this.name);
}
var person = new Person("George");
कुछ महत्वपूर्ण बिंदु हैं जिन्हें हमें प्रोटोटाइप अवधारणा से गुजरने से पहले विचार करना होगा।
1- वास्तव में जावास्क्रिप्ट कैसे काम करता है:
पहला कदम उठाने के लिए हमें यह पता लगाना होगा कि वास्तव में जावास्क्रिप्ट कैसे कार्य करता है, एक वर्ग के रूप में कार्य करता है जैसे this
कि इसमें कीवर्ड का उपयोग करना या सिर्फ अपने तर्कों के साथ एक नियमित कार्य के रूप में, यह क्या करता है और क्या देता है।
मान लें कि हम Person
ऑब्जेक्ट मॉडल बनाना चाहते हैं । लेकिन इस चरण में मैं उपयोग prototype
और new
कीवर्ड के बिना एक ही सटीक काम करने की कोशिश कर रहा हूं ।
तो इस चरण में functions
, objects
और this
कीवर्ड, क्या हमारे पास सभी हैं।
पहला सवाल होगा कैसे this
कीवर्ड का उपयोग किए बिना उपयोगी हो सकता है new
कीवर्ड ।
तो उत्तर देने के लिए कि मान लें कि हमारे पास एक खाली वस्तु है, और दो कार्य हैं:
var person = {};
function Person(name){ this.name = name; }
function getName(){
console.log(this.name);
}
और अब कीवर्ड के बिनाnew
हम इन कार्यों का उपयोग कैसे कर सकते हैं। इसलिए जावास्क्रिप्ट के 3 अलग-अलग तरीके हैं:
ए। पहला तरीका केवल फ़ंक्शन को एक नियमित फ़ंक्शन के रूप में कॉल करना है:
Person("George");
getName();//would print the "George" in the console
इस मामले में, यह वर्तमान संदर्भ वस्तु होगी, जो आमतौर पर window
ब्राउज़र या GLOBAL
में वैश्विक वस्तु होती है Node.js
। इसका अर्थ है कि हमारे पास Node.js में ब्राउजर या GLOBAL.name में window.name, "जॉर्ज" इसके मूल्य के रूप में होगा।
ख। हम उन्हें एक वस्तु से जोड़ सकते हैं , इसके गुणों के रूप में
- ऐसा करने का सबसे आसान तरीका खाली person
वस्तु को संशोधित करना है , जैसे:
person.Person = Person;
person.getName = getName;
इस तरह हम उन्हें कॉल कर सकते हैं जैसे:
person.Person("George");
person.getName();// -->"George"
और अब person
वस्तु की तरह है:
Object {Person: function, getName: function, name: "George"}
- किसी वस्तु को किसी संपत्ति में संलग्न करने का दूसरा तरीका उस वस्तु का उपयोग करना prototype
है जिसे किसी भी जावास्क्रिप्ट वस्तु में पाया जा सकता है जिसका नाम है __proto__
, और मैंने इसे सारांश भाग पर थोड़ा समझाने की कोशिश की है। इसलिए हम ऐसा करके ही परिणाम प्राप्त कर सकते हैं:
person.__proto__.Person = Person;
person.__proto__.getName = getName;
लेकिन इस तरह से जो हम वास्तव में कर रहे हैं वह संशोधित कर रहा है Object.prototype
, क्योंकि जब भी हम शाब्दिक ( { ... }
) का उपयोग करके एक जावास्क्रिप्ट ऑब्जेक्ट बनाते हैं , तो यह आधार पर बनाया जाता है Object.prototype
, जिसका अर्थ है कि यह एक विशेषता नाम के रूप में नई बनाई गई वस्तु से जुड़ा हुआ है __proto__
, इसलिए यदि हम इसे बदलते हैं , जैसा कि हमने अपने पिछले कोड स्निपेट पर किया है, सभी जावास्क्रिप्ट ऑब्जेक्ट बदल जाएंगे, एक अच्छा अभ्यास नहीं। तो अब बेहतर अभ्यास क्या हो सकता है:
person.__proto__ = {
Person: Person,
getName: getName
};
और अब अन्य वस्तुएँ शांति में हैं, लेकिन यह अभी भी एक अच्छा अभ्यास नहीं लगता है। इसलिए हमारे पास अभी भी एक और समाधान है, लेकिन इस समाधान का उपयोग करने के लिए हमें उस कोड की उस पंक्ति पर वापस जाना चाहिए जहां person
ऑब्जेक्ट बनाया गया ( var person = {};
) तब इसके लिए इसे निम्न करें:
var propertiesObject = {
Person: Person,
getName: getName
};
var person = Object.create(propertiesObject);
यह क्या करता है एक नया जावास्क्रिप्ट बना रहा है Object
और विशेषता propertiesObject
को संलग्न करता है __proto__
। तो यह सुनिश्चित करने के लिए कि आप क्या कर सकते हैं:
console.log(person.__proto__===propertiesObject); //true
लेकिन यहां मुश्किल बिंदु यह है कि आपके पास ऑब्जेक्ट __proto__
के पहले स्तर पर परिभाषित सभी गुणों तक पहुंच है person
(अधिक विस्तार के लिए सारांश भाग पढ़ें)।
जैसा कि आप इन दो तरीकों में से किसी का उपयोग करते हुए देखते हैं, this
यह वास्तव में person
ऑब्जेक्ट को इंगित करेगा ।
सी। जावास्क्रिप्ट के पास फ़ंक्शन प्रदान करने का एक और तरीका है this
, जो फ़ंक्शन का उपयोग करने के लिए कॉल या एप्लिकेशन का उपयोग कर रहा है।
लागू () विधि एक दिए गए इस मान और एक सरणी (या एक सरणी जैसी वस्तु) के रूप में दिए गए तर्कों के साथ एक फ़ंक्शन को कॉल करती है।
तथा
कॉल () विधि किसी दिए गए इस मान और व्यक्तिगत रूप से प्रदान किए गए तर्कों के साथ एक फ़ंक्शन को कॉल करती है।
इस तरह जो मेरा पसंदीदा है, हम आसानी से अपने कार्यों को कॉल कर सकते हैं जैसे:
Person.call(person, "George");
या
//apply is more useful when params count is not fixed
Person.apply(person, ["George"]);
getName.call(person);
getName.apply(person);
ये 3 विधियाँ .prototyp कार्यक्षमता का पता लगाने के लिए महत्वपूर्ण प्रारंभिक चरण हैं।
2- new
कीवर्ड कैसे काम करता है?
.prototype
कार्यक्षमता को समझने के लिए यह दूसरा चरण है। इस प्रक्रिया का अनुकरण करने के लिए मैं इसका उपयोग करता हूं:
function Person(name){ this.name = name; }
my_person_prototype = { getName: function(){ console.log(this.name); } };
इस भाग में, मैं उन सभी चरणों को लेने की कोशिश कर रहा हूँ जो जावास्क्रिप्ट का उपयोग करता है, बिना new
कीवर्ड का उपयोग किए और prototype
, जब आप new
कीवर्ड का उपयोग करते हैं । इसलिए जब हम कार्य करते हैं new Person("George")
, तो Person
फ़ंक्शन एक निर्माता के रूप में कार्य करता है, ये वही हैं जो जावास्क्रिप्ट करता है, एक-एक करके:
ए। सबसे पहले यह एक खाली वस्तु बनाता है, मूल रूप से एक खाली हैश जैसे:
var newObject = {};
ख। अगला कदम जो जावास्क्रिप्ट लेता है, वह है कि सभी प्रोटोटाइप ऑब्जेक्ट्स को नई बनाई गई वस्तु से जोड़ना
हमारे my_person_prototype
यहाँ प्रोटोटाइप ऑब्जेक्ट के समान है।
for(var key in my_person_prototype){
newObject[key] = my_person_prototype[key];
}
यह तरीका नहीं है कि जावास्क्रिप्ट वास्तव में उन गुणों को संलग्न करता है जो प्रोटोटाइप में परिभाषित होते हैं। वास्तविक तरीका प्रोटोटाइप चेन अवधारणा से संबंधित है।
ए। और बी। इन दो चरणों के बजाय आप एक ही परिणाम कर सकते हैं:
var newObject = Object.create(my_person_prototype);
//here you can check out the __proto__ attribute
console.log(newObject.__proto__ === my_person_prototype); //true
//and also check if you have access to your desired properties
console.log(typeof newObject.getName);//"function"
अब हम अपने में getName
फंक्शन को कॉल कर सकते हैं my_person_prototype
:
newObject.getName();
सी। तब यह उस निर्माणकर्ता को वस्तु देता है,
हम अपने नमूने के साथ ऐसा कर सकते हैं:
Person.call(newObject, "George");
या
Person.apply(newObject, ["George"]);
तब कंस्ट्रक्टर जो चाहे कर सकता है, क्योंकि यह उस कंस्ट्रक्टर के अंदर की वस्तु है जिसे अभी बनाया गया था।
अब अन्य चरणों का अनुकरण करने से पहले अंतिम परिणाम: ऑब्जेक्ट {नाम: "जॉर्ज"}
सारांश:
मूल रूप से, जब आप किसी फ़ंक्शन पर नए कीवर्ड का उपयोग करते हैं, तो आप उस पर कॉल कर रहे हैं और वह फ़ंक्शन एक निर्माता के रूप में कार्य करता है, इसलिए जब आप कहते हैं:
new FunctionName()
जावास्क्रिप्ट आंतरिक रूप से एक वस्तु बनाता है, एक खाली हैश और फिर वह उस वस्तु को कंस्ट्रक्टर को देता है, फिर कंस्ट्रक्टर जो चाहे वह कर सकता है, क्योंकि इस कंस्ट्रक्टर के अंदर वह वस्तु है जिसे अभी बनाया गया था और फिर यह आपको उस वस्तु को प्रदान करता है यदि आपने अपने फ़ंक्शन में रिटर्न स्टेटमेंट का उपयोग नहीं किया है या यदि आपने return undefined;
अपने फ़ंक्शन बॉडी के अंत में रखा है ।
इसलिए जब जावास्क्रिप्ट किसी वस्तु पर एक संपत्ति को देखने जाता है, तो पहली चीज जो वह करता है, क्या वह उस वस्तु पर दिखता है। और फिर एक गुप्त संपत्ति है [[prototype]]
जो हमारे पास आमतौर पर पसंद है __proto__
और वह संपत्ति है जो जावास्क्रिप्ट अगले पर दिखती है। और जब वह इसके माध्यम से देखता है __proto__
, जहां तक यह फिर से एक और जावास्क्रिप्ट ऑब्जेक्ट है, इसकी अपनी __proto__
विशेषता है, यह ऊपर और ऊपर जाता है जब तक कि यह उस बिंदु तक नहीं जाता है जहां अगला __proto__
शून्य है। बिंदु जावास्क्रिप्ट में केवल उद्देश्य यह है कि इसकी है __proto__
विशेषता मान शून्य होगा Object.prototype
वस्तु:
console.log(Object.prototype.__proto__===null);//true
और यह है कि जावास्क्रिप्ट में वंशानुक्रम कैसे काम करता है।
दूसरे शब्दों में, जब आपके पास किसी फ़ंक्शन पर एक प्रोटोटाइप प्रॉपर्टी होती है और आप उस पर एक नया कॉल करते हैं, तो जावास्क्रिप्ट संपत्तियों के लिए उस नए बनाए गए ऑब्जेक्ट को देखने के बाद, यह फ़ंक्शन पर नज़र डालेगा .prototype
और यह भी संभव है कि यह ऑब्जेक्ट उसके पास हो। खुद के आंतरिक प्रोटोटाइप। और इसी तरह।