रेफरेंस-काउंटिंग गार्बेज कलेक्शन
सबसे सरल GC एल्गोरिदम: प्रत्येक ऑब्जेक्ट का रेफरेंस काउंट ट्रैक करता है। काउंट 0 होने पर ऑब्जेक्ट कलेक्टेबल।
कैसे काम करता है
<script>
var obj = { x: { y: 2 } }; // 2 ऑब्जेक्ट्स बने
// obj → {x: {...}} (काउंट 1)
// obj.x → {y: 2} (काउंट 1)
obj = 1; // obj अब नंबर रेफर करता है
// पहला ऑब्जेक्ट: काउंट 0 → कलेक्टेबल
// दूसरा ऑब्जेक्ट (obj.x): काउंट 0 → कलेक्टेबल
</script>
सीमा: सर्कुलर रेफरेंस (Cycles)
दो ऑब्जेक्ट्स एक-दूसरे को रेफर करें → दोनों का काउंट ≥1 → कभी कलेक्ट नहीं (भले ही अनपहुंच योग्य हों)।
<script>
function f() {
var obj1 = {};
var obj2 = {};
obj1.p = obj2; // obj1 → obj2
obj2.p = obj1; // obj2 → obj1 (साइकिल!)
// फंक्शन खत्म: दोनों आउट ऑफ स्कोप
// लेकिन रेफरेंस काउंट 1-1 → GC नहीं करेगा ❌
}
f();
</script>
इतिहास: IE6/7 में समस्या
- DOM: रेफरेंस काउंटिंग
- JS इंजन: मार्क-एंड-स्वीप
- क्रॉस-रेफरेंस (JS ↔ DOM) → लीक
- आधुनिक ब्राउज़र्स: दोनों मार्क-एंड-स्वीप → हल
क्यों अब उपयोग नहीं होता?
| पहलू | रेफरेंस काउंटिंग | मार्क-एंड-स्वीप |
|---|---|---|
| सर्कुलर रेफरेंस | ❌ फेल | ✅ हैंडल करता है |
| ओवरहेड | हर असाइनमेंट पर काउंट अपडेट | पीरियॉडिक स्कैन |
| पॉज टाइम | छोटे, लगातार | बड़े, कभी-कभी |
| रियल-टाइम | बेहतर | कठिन |
आधुनिक उपयोग
कुछ सिस्टम्स में अभी भी उपयोगी:
- C++
shared_ptr(साइकिल्स के लिएweak_ptr) - Python (साइकिल डिटेक्टर के साथ)
- PHP, Objective-C (ARC)
- कुछ एम्बेडेड JS इंजन्स
निष्कर्ष
JavaScript इंजन्स (V8, SpiderMonkey, JavaScriptCore, Chakra) मार्क-एंड-स्वीप और इसके वेरिएंट्स उपयोग करते हैं। रेफरेंस काउंटिंग ऐतिहासिक संदर्भ के लिए महत्वपूर्ण।