परिचय: आपकी वेबसाइट "धीमी" क्यों है, और इसके लिए कौन जिम्मेदार है
\n\nएक ऐसे रेस्तरां की कल्पना करें जहाँ एक ही वेटर एक साथ ऑर्डर लेता है, खाना परोसता है, बर्तन धोता है और बिल का हिसाब लगाता है। अव्यवस्था, है ना? लगभग ऐसे ही सिंगल-थ्रेडेड जावास्क्रिप्ट काम करता है, अगर टास्क को सही ढंग से मैनेज न किया जाए। जब हम ऐसा कोड लिखते हैं जो सब कुछ एक साथ करता है — डेटा लोड करना, क्लिक प्रोसेस करना, एनिमेशन बनाना — तो ब्राउज़र रुक जाता है, और उपयोगकर्ता को एक "सोचने वाला" इंटरफ़ेस दिखाई देता है।
\n\nआज हम समझेंगे कि कैसे जावास्क्रिप्ट में टास्क कतारें इस अव्यवस्था को एक व्यवस्थित प्रणाली में बदलने में मदद करती हैं। आप जानेंगे कि Event Loop प्राथमिकताएँ कैसे वितरित करता है, माइक्रोटास्क मैक्रोटास्क से कैसे भिन्न होते हैं, और कैसे जावास्क्रिप्ट बैकग्राउंड टास्क मुख्य थ्रेड को ब्लॉक नहीं होने देते। अंत में, आपको व्यावहारिक उदाहरण मिलेंगे जिन्हें आप तुरंत अपने प्रोजेक्ट में लागू कर सकते हैं।
\n\nEvent Loop कैसे काम करता है: टास्क ऑर्केस्ट्रा का संचालक
\n\nसभी एसिंक्रोनसिटी के केंद्र में Event Loop JavaScript है। यह एक ऐसा तंत्र है जो लगातार घूमता रहता है और पूछता है: "क्या करने के लिए कुछ है? माइक्रोटास्क? रेंडरिंग?"। यदि आपने कभी सोचा है कि setTimeout तुरंत क्यों नहीं चलता, जबकि Promise.then लगभग तुरंत चलता है — तो इसका उत्तर यहीं छिपा है।
कॉल स्टैक (Call Stack)
\nयह वह स्थान है जहाँ तत्काल निष्पादन के लिए फ़ंक्शन आते हैं। जब तक स्टैक व्यस्त है, कुछ और नहीं होगा। यदि आपका फ़ंक्शन दस लाख संख्याओं की गणना करता है — ब्राउज़र रुक जाएगा, क्योंकि स्टैक खाली नहीं होगा।
\n\nमैक्रोटास्क कतार (Macrotask Queue)
\nइसमें setTimeout, setInterval, DOM इवेंट (क्लिक, स्क्रॉल), संसाधन लोडिंग आते हैं। Event Loop इस कतार से एक-एक करके टास्क लेता है, उसे निष्पादित करता है, फिर माइक्रोटास्क की जाँच करता है, फिर पेज रेंडर करता है — और फिर अगला मैक्रोटास्क लेता है।
माइक्रोटास्क कतार (Microtask Queue)
\nयह Promise, queueMicrotask, MutationObserver का राज्य है। माइक्रोटास्क की सर्वोच्च प्राथमिकता होती है। जैसे ही स्टैक खाली होता है, Event Loop अगले मैक्रोटास्क पर जाने से पहले सभी माइक्रोटास्क को निष्पादित करता है। यही कारण है कि Promise.resolve().then(), setTimeout से तेज़ चलता है।
console.log('1');\n\nsetTimeout(() => {\n console.log('2');\n}, 0);\n\nPromise.resolve().then(() => {\n console.log('3');\n});\n\nconsole.log('4');\n\n// आउटपुट: 1, 4, 3, 2\n\n\nयह उदाहरण क्लासिक है। setTimeout (मैक्रोटास्क) शून्य विलंब के साथ भी विलंबित होता है, जबकि Promise.then (माइक्रोटास्क) सिंक्रोनस कोड के तुरंत बाद निष्पादित होता है। इस क्रम को समझना पूर्वानुमानित एसिंक्रोनस कोड लिखने की कुंजी है।
बैकग्राउंड टास्क: इंटरफ़ेस को कैसे ब्लॉक न करें
\n\nअब मुख्य समस्या: क्या करें यदि भारी काम करना हो (इमेज प्रोसेसिंग, जटिल गणना, डेटा पार्सिंग)? यदि इसे मुख्य थ्रेड पर चलाया जाए — इंटरफ़ेस रुक जाएगा। समाधान है — जावास्क्रिप्ट बैकग्राउंड टास्क।
\n\nWeb Workers — वास्तविक मल्टीथ्रेडिंग
\nWeb Workers JS कोड को एक अलग थ्रेड में चलाने की अनुमति देते हैं। इसकी DOM तक पहुँच नहीं है, लेकिन यह मुख्य थ्रेड के साथ संदेशों का आदान-प्रदान कर सकता है। यह बैकग्राउंड में JS कतार प्रोसेसिंग के लिए एक आदर्श उपकरण है।
\n\n// main.js\nconst worker = new Worker('worker.js');\n\nworker.postMessage({ data: [1, 2, 3, 4, 5, 6] });\n\nworker.onmessage = (event) => {\n console.log('वर्कर से परिणाम:', event.data);\n};\n\n// worker.js\nself.onmessage = (event) => {\n const numbers = event.data.data;\n // भारी काम: सम संख्याओं को फ़िल्टर करना\n const result = numbers.filter(n => n % 2 === 0);\n self.postMessage(result);\n};\n\n\nध्यान दें: मुख्य थ्रेड ब्लॉक नहीं होता। उपयोगकर्ता क्लिक कर सकता है, स्क्रॉल कर सकता है, टेक्स्ट टाइप कर सकता है — सब कुछ सुचारू रूप से काम करेगा, जबकि वर्कर गणना कर रहा है।
\n\n