क्या जावास्क्रिप्ट में "कमजोर संदर्भ" बनाना संभव है?


98

क्या किसी अन्य वस्तु को "कमजोर संदर्भ" बनाने के लिए जावास्क्रिप्ट में कोई रास्ता है? यहाँ विकी पृष्ठ का वर्णन है जो एक कमजोर संदर्भ है। यहाँ एक और लेख है जो जावा में उनका वर्णन करता है। क्या कोई इस व्यवहार को जावास्क्रिप्ट में लागू करने का तरीका सोच सकता है?


4
ES6 के लिए कमजोर संदर्भों पर चर्चा की जा रही है। अपनी आँखें खुली रखें।
रयान स्मिथ

2
* आधिकारिक युक्ति wiki / चर्चा wiki.ecmascript.org/doku.php?id=strawman:weak_refs पर , वर्तमान में "अंतिम संशोधित: 2013/02/02 22:25" * esdiscuss.org.topic / what पर कुछ अन्य कल्पना चर्चा -इस-की-स्थिति-कमजोर-संदर्भ , वर्तमान में अंतिम पोस्ट "सूर्य मार्च 3 11:56:05 पीएसटी 2013"
नियति वास्तुकार

ज्यादातर मामलों में WR, लैप्सड श्रोता समस्या को हल करने का एक प्रयास है , यहाँ चर्चा की गई है: [ stackoverflow.com/questions/43758217/… । अगर उस सवाल का एक अच्छा जवाब होता तो मुझे नहीं लगता कि WRs की ज्यादा जरूरत होती।
जेम्स

@supercat मैंने व्यपगत श्रोता प्रश्न का उत्तर पोस्ट किया है ।
जेम्स

जवाबों:


39

जावास्क्रिप्ट में कमजोरियों के लिए कोई भाषा समर्थन नहीं है। आप मैनुअल रेफरेंस काउंटिंग का उपयोग कर अपना रोल कर सकते हैं, लेकिन विशेष रूप से सुचारू रूप से नहीं। आप प्रॉक्सी रैपर ऑब्जेक्ट नहीं बना सकते, क्योंकि जावास्क्रिप्ट ऑब्जेक्ट्स में कभी पता नहीं चलता कि वे कब कचरा इकट्ठा करने वाले हैं।

तो आपका 'कमजोर संदर्भ' एक साधारण लुकअप में एक ऐड-रेफरेंस और रिमूवल-रेफरेंस मेथड के साथ एक कुंजी (जैसे पूर्णांक) बन जाता है, और जब मैन्युअल रूप से ट्रैक किए गए संदर्भ नहीं रह जाते हैं तो भविष्य के लुकअप को छोड़कर एंट्री को डिलीट किया जा सकता है। अशक्त लौटने की कुंजी।

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


2
मैंने कोड की सावधानीपूर्वक जांच (या उपयोग) नहीं की है, लेकिन es-lab में एक स्क्रिप्ट है जो मूल WeakMap अनुकरण प्रदान करती हैऑरोरा 6 (मोज़िला) में एक गैर-मानक WeakMap कार्यान्वयन है
थेजुरशादो

2
ES6 के साथ यह उत्तर अब सही नहीं है। मेरे जवाब के नीचे देखें stackoverflow.com/a/28567560/745190
thelastshadow

9
यह अभी भी सही है, क्योंकि ES6 WeakMaps सही कमजोर संदर्भ नहीं हैं। WeakMaps केवल कुंजी के रूप में वस्तुओं को स्वीकार करते हैं, और इन वस्तुओं के संदर्भ को कमजोर रूप से आयोजित किया जाता है। देखें stackoverflow.com/questions/32397729/…
CodeManX

मैंने एक कमजोर मानचित्र का अनुकरण करने के लिए एक कक्षा लिखी और उसे यहाँ पोस्ट किया: stackoverflow.com/a/47017206/491553
रायन


11

अपडेट: सितंबर 2019

कमजोर संदर्भों का उपयोग करना अभी तक संभव नहीं है, लेकिन सबसे अधिक संभावना है कि यह जल्द ही संभव होगा, क्योंकि जावास्क्रिप्ट में WeakRefs वर्क इन प्रोग्रेस हैं। नीचे दिए गए विवरण।

प्रस्ताव

अब चरण 3 में प्रस्ताव जिसका अर्थ है कि इसकी पूरी विशिष्टता है और आगे शोधन में कार्यान्वयन और उपयोगकर्ताओं से प्रतिक्रिया की आवश्यकता होगी।

WeakRef प्रस्ताव कार्यक्षमता के दो प्रमुख नए टुकड़े शामिल हैं:

  • WeakRef वर्ग के साथ वस्तुओं का कमजोर संदर्भ बनाना
  • ऑब्जेक्ट के बाद उपयोगकर्ता-परिभाषित फ़ाइनलिज़र चलाना, कचरा एकत्र करना, फ़ाइनलिज़ेशनग्रुप क्लास के साथ है

बक्सों का इस्तेमाल करें

कमजोर संदर्भों के लिए एक प्राथमिक उपयोग बड़ी वस्तुओं को धारण करने वाले कैश या मैपिंग को लागू करना है, जहां यह वांछित है कि एक बड़ी वस्तु को केवल जीवित नहीं रखा जाता है क्योंकि यह कैश या मैपिंग में प्रकट होता है।

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

स्रोत और आगे पढ़ने

https://github.com/tc39/proposal-weakrefs
https://v8.dev/features/wit-wferences


1
फ़ायरफ़ॉक्स नाइटली ने WeakRef के लिए प्रयोगात्मक समर्थन जोड़ा है। WeakSet के चलने योग्य संस्करण बनाने के लिए इसका उपयोग करने का एक उदाहरण यहां दिया गया है: gist.github.com/seanlinsley/bc10378fd311d75cf6b5e80394be813d
Seanlinsley

3

सही कमजोर संदर्भ, नहीं, अभी तक नहीं (लेकिन ब्राउज़र निर्माता विषय को देख रहे हैं)। लेकिन यहां एक विचार है कि कमजोर संदर्भों का अनुकरण कैसे किया जाए।

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

जब आपको किसी वस्तु की आवश्यकता होती है, तो आप उसके लिए कैश पूछते हैं। यदि कैश में ऑब्जेक्ट है, तो उसे वापस कर दिया जाता है। यदि यह नहीं है, तो आइटम उत्पन्न होता है, संग्रहीत किया जाता है, और फिर वापस आ जाता है।

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

विलोपन एल्गोरिथ्म कुंजी है, क्योंकि अगर आपको यह गलत लगता है तो आप सबसे लोकप्रिय वस्तुओं को हटा सकते हैं। यह भयानक प्रदर्शन का कारण होगा।

जब तक कैश संग्रहीत ऑब्जेक्ट्स के स्थायी संदर्भों के साथ एकमात्र ऑब्जेक्ट है , तब तक उपरोक्त सिस्टम को सच्चे कमजोर संदर्भों के विकल्प के रूप में बहुत अच्छी तरह से काम करना चाहिए।


25
क्या आपने कमजोरों को अप्रासंगिक कहा है?
एरिक कपलुन

22
@ JL235 - कमजोर संदर्भों के लिए महत्वपूर्ण उपयोग कैश के लिए नहीं बल्कि इवेंट-हैंडलर के लिए है। मेरे पास कुछ ऑब्जेक्ट है, जबकि यह मौजूद है, किसी अन्य घटना का निरीक्षण करना चाहिए - लेकिन मैं इस तथ्य को नहीं चाहता कि यह जीसी के प्रयोजनों के लिए एक संदर्भ बनाने के लिए अधिसूचना-सूची में है।
माल्वोलियो

7
कमजोर संदर्भों का कैशिंग से कोई लेना-देना नहीं है। एक कमजोर संदर्भ का मतलब है कि आप किसी चीज़ पर नज़र रखना चाहते हैं, लेकिन अगर किसी वस्तु का पता नहीं लगाया जा रहा है, तो आप उसे हटा सकते हैं।
फैबस्प्रो

8
स्वत: समाप्ति के लिए कमजोर संदर्भों का उपयोग करके कैश बनाने के लिए स्पष्ट रूप से उपयोग का मामला है।
फिल फ्रीमैन

5
कैशिंग पारंपरिक रूप से कमजोर संदर्भों का एक शीर्ष कारण है। घटना हैंडलर डोम बात केवल कुछ IE एक्सप्लोरर छोटी गाड़ी बात है।
axkibe


2

एक कमजोर संदर्भ का अनुकरण करने के लिए एक कैशिंग तंत्र का उपयोग करना, जैसा कि ऊपर जेएल 235 ने सुझाव दिया है , उचित है। यदि कमजोर संदर्भ मूल रूप से मौजूद होंगे, तो आप इस तरह का व्यवहार करेंगे:

this.val = {};
this.ref = new WeakReference(this.val);
...
this.ref.get(); // always returns val
...
this.val = null; // no more references
...
this.ref.get(); // may still return val, depending on already gc'd or not

जबकि कैश के साथ आप देख सकते हैं:

this.val = {};
this.key = cache.put(this.val);
...
cache.get(this.key); // returns val, until evicted by other cache puts
...
this.val = null; // no more references
...
cache.get(this.key); // returns val, until evicted by other cache puts

एक संदर्भ के धारक के रूप में, आपको इस बारे में कोई धारणा नहीं बनानी चाहिए कि यह कब किसी मूल्य को संदर्भित करता है, यह कैश का उपयोग करके अलग नहीं है



-4

EcmaScript 6 (ES हार्मनी) में वीकएप ऑब्जेक्ट है। आधुनिक ब्राउज़रों के बीच ब्राउज़र का समर्थन बहुत अच्छा है (फ़ायरफ़ॉक्स, क्रोम और यहां तक ​​कि आगामी IE संस्करण का अंतिम 3 संस्करण इसका समर्थन करते हैं)।


29
यह बिल्कुल वैसा ही नहीं है। A WeakMapवस्तुओं को कमजोर संदर्भ नहीं देता है- यह वे मान नहीं है जो WeakMap में कमजोर संदर्भ हैं, लेकिन चाबियाँ । तथ्य यह है कि मानचित्र में कमजोर संदर्भ मौजूद हैं, केवल स्मृति रिसाव निवारण तंत्र है, और अन्यथा उपयोगकर्ता के लिए अवलोकन योग्य नहीं है।
आईसेश

1
आप सही हैं कि यह कुंजी है जो कमजोर हैं, न कि मान। लेकिन कमजोर संदर्भों का उपयोग करने का पूरा उद्देश्य संदर्भित वस्तु के कचरा संग्रह की अनुमति देना है। ओपी ने दो लिंक पोस्ट किए, जिनमें से दूसरा एक ऑब्जेक्ट को एक आईडी जोड़ने के बारे में है जिसे आप विस्तारित नहीं कर सकते हैं, और वास्तव में यह WeakHashMap, जावास्क्रिप्ट के WeakMap के जावा समकक्ष का उपयोग करने की सिफारिश करता है।
बजकर

12
सौभाग्य WeakMap का उपयोग कर के बाद से एक कमजोर संदर्भ लागू करने के लिए weakmap.get(new String('any possible key that has ever existed or ever will exist'))होगा हमेशा हो undefined। उपयोगी नहीं है। नीचे मतदान!
user3338098

-5

http://www.jibbering.com/faq/faq_notes/closures.html

ECMAScript स्वचालित कचरा संग्रहण का उपयोग करता है। विनिर्देश विवरण को परिभाषित नहीं करता है, जिससे कि कार्यान्वयनकर्ताओं को छाँटना हो, और कुछ कार्यान्वयन उनके कचरा संग्रहण कार्यों को बहुत कम प्राथमिकता देने के लिए जाने जाते हैं। लेकिन सामान्य विचार यह है कि यदि कोई वस्तु बिना संदर्भ वाली हो जाती है (शेष संदर्भ नहीं होने से कोड को क्रियान्वित करने के लिए सुलभ छोड़ दिया जाता है) तो यह कचरा संग्रहण के लिए उपलब्ध हो जाती है और भविष्य के किसी भी बिंदु पर नष्ट हो जाएगी और किसी भी संसाधन से मुक्त और वापस आ रहा है। पुन: उपयोग के लिए सिस्टम को।

यह आमतौर पर एक निष्पादन संदर्भ से बाहर निकलने पर मामला होगा। गुंजाइश श्रृंखला संरचना, सक्रियण / चर वस्तु और निष्पादन वस्तुओं के भीतर बनाई गई कोई भी वस्तु, फ़ंक्शन ऑब्जेक्ट सहित, अब सुलभ नहीं होगी और इसलिए कचरा संग्रहण के लिए उपलब्ध होगी।

मतलब केवल कमजोर ही नहीं हैं जो अब उपलब्ध नहीं हैं।


10
संदर्भ चक्र से बचना कमजोर संदर्भों का उपयोग करने का एकमात्र कारण नहीं है। वे वस्तु उदाहरण पूलिंग / कैशिंग और इतने पर के लिए बहुत उपयोगी हैं।
शराबी

WeakReference की परिभाषा प्रश्न का नहीं है। जैसा कि ऊपर टिप्पणी के साथ सहमत हूँ।
यूरी यारशेव
हमारी साइट का प्रयोग करके, आप स्वीकार करते हैं कि आपने हमारी Cookie Policy और निजता नीति को पढ़ और समझा लिया है।
Licensed under cc by-sa 3.0 with attribution required.