मैं आरएक्सजेएस सीख रहा हूं और इसके बजाय उलझन में हूं कि "श्रोता" कहां हैं (अवलोकन योग्य या पर्यवेक्षक में), वे कैसे सब्सक्राइब/अनसब्सक्राइब किए जाते हैं, और क्या होता है जब एक पर्यवेक्षक "अब एक अवलोकन योग्य" में रूचि नहीं रखता है, जैसे जब आप take या takeUntil का उपयोग करते हैं।

पहले भाग के लिए - क्या सब्सक्राइब किया गया है, श्रोता क्या है - मैं इन बयानों के बीच प्रतीत होने वाले विरोधाभास से भ्रमित हूं। http://reactivex.io/rxjs/manual/overview.html से हम पढ़ते हैं कि पर्यवेक्षक वेधशालाओं के 'श्रोता' नहीं हैं

यह ईवेंट हैंडलर एपीआई जैसे addEventListener/removeEventListener के लिए काफी अलग है। ऑब्जर्वेबल.सब्सक्राइब के साथ, दिए गए ऑब्जर्वर ऑब्जर्वेबल में श्रोता के रूप में पंजीकृत नहीं होते हैं। ऑब्जर्वेबल संलग्न पर्यवेक्षकों की सूची भी नहीं रखता है।

लेकिन http://reactivex.io/learnrx/ में यह कहता है (व्यायाम 30) (मेरा हाइलाइट करना) कि

किसी घटना पर आधारित ऑब्जर्वेबल कभी भी अपने आप पूरा नहीं होगा। NS take () फ़ंक्शन एक नया अनुक्रम बनाता है जो असतत के बाद पूरा होता है मदों की संख्या आती है। यह महत्वपूर्ण है, क्योंकि किसी ईवेंट के विपरीत, जब एक अवलोकनीय अनुक्रम पूरा हो जाता है तो यह उसकी सभी सदस्यता समाप्त कर देता है श्रोता. इसका मतलब है कि अगर हम अपने ईवेंट को पूरा करने के लिए टेक () का उपयोग करते हैं अनुक्रम, हमें सदस्यता समाप्त करने की आवश्यकता नहीं है!

यह मेरे लिए विरोधाभासी लगता है। जब आप एक ऑब्जर्वेबल सेट करते हैं, उदाहरण के लिए, fromEvent, तो ईवेंट श्रोता कहाँ होता है? जब आप take(1) का उपयोग करते हैं, उदाहरण के लिए, DOM ईवेंट पर आधारित ऑब्जर्वेबल पर, ऑब्जर्वर को पहला ईवेंट भेजे जाने के बाद क्या होता है? क्या ऑब्जर्वेबल से ऑब्जर्वर अनसब्सक्राइब करता है, जो लगातार घटनाओं का उत्सर्जन करता है, यह सिर्फ इतना है कि ऑब्जर्वर अब उन्हें नहीं सुन रहा है? या ऑब्जर्वेबल किसी तरह ऑब्जर्वर को अनसब्सक्राइब करता है, यानी इवेंट लिस्टनर ऑब्जर्वेबल में था, ऑब्जर्वर में नहीं?

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

1
Cerulean 9 सितंबर 2019, 19:51

1 उत्तर

सबसे बढ़िया उत्तर

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

मुझे यह बताने की कोशिश करें कि मेरा क्या मतलब है जब मैं कहता हूं कि एक अवलोकन योग्य की सदस्यता लेना कार्यों की एक श्रृंखला को कॉल करने का मामला है। निम्नलिखित सुपर सरल उदाहरण पर विचार करें:

एक सुपर सरल उदाहरण के लिए, मान लीजिए कि मैं इसे देखने योग्य बनाता हूं:

const justOne = Rx.Observable.create(function realSubscribe(observer) {
  observer.next(1);
  observer.complete();
});

justOne.subscribe(val => console.log(val));

अगर मैं फिर justOne.subscribe(val => console.log(val)) को कॉल करता हूं, तो ऐसा करने पर मेरे द्वारा रियल सबस्क्राइब नाम के फंक्शन को तुरंत कॉल कर दिया जाएगा। यह तब observer.next(1) करता है, जिसके परिणामस्वरूप वैल लॉग आउट होता है, फिर यह observer.complete() करता है। और बस।

इस प्रक्रिया में कहीं भी देखने योग्य ने ग्राहकों की सूची नहीं बनाई या वृद्धि नहीं की; यह सिर्फ क्रमिक रूप से कोड के माध्यम से चला और फिर किया गया।


अब थोड़ा और यथार्थवादी उदाहरण की ओर बढ़ते हुए, आइए fromEvent पर विचार करें। अगर मैं इसे लागू करता, तो यह कुछ इस तरह दिखाई दे सकता है (वास्तविक कार्यान्वयन अधिक जटिल है, लेकिन इसका सार यह है):

function fromEvent(element, eventName) {
  return Rx.Observable.create(function subscribeToEvent(observer) {
    element.addEventListener(eventName, observer.next);
    return function cleanup() {
      element.removeEventListener(eventName, observer.next);
    }
  });
}

const observable = fromEvent(document, 'click');
const subscription = observable.subscribe(event => console.log(event));

अब जब मैं ऑब्जर्वेबल को कॉल करता हूं। document.addEventListener करता है दस्तावेज़ में ईवेंट श्रोताओं की एक सूची रखी जाती है, लेकिन इसका कारण यह है कि जिस तरह से addEventListener लागू किया गया है, सभी अवलोकनों के लिए कुछ सामान्य नहीं है। देखने योग्य स्वयं किसी श्रोता का ट्रैक नहीं रखता है। यह केवल वही कॉल करता है जिसे कॉल करने के लिए कहा गया है, और फिर एक क्लीनअप फ़ंक्शन देता है।


आगे आइए टेक पर नजर डालते हैं। पहले की तरह वास्तविक कार्यान्वयन अधिक जटिल है , लेकिन यहाँ मोटे तौर पर यह क्या करता है:

// In the real `take`, you don't need to pass in another observable since that's
// available automatically from the context you called it in. But my sample code
// has to get it somehow.
function take(count, otherObservable) {
  return new Observable(function subscribeToTake(observer) {
    let soFar = 0;
    otherObservable.subscribe((value) => {
      observer.next(value);
      soFar++;
      if (soFar >= count) {
        observer.complete();
      }
    });
  });
}

const clickObservable = fromEvent(document, 'click');
take(1, clickObservable).subscribe(event => console.log(event))

जैसा कि टिप्पणी में उल्लेख किया गया है, मैं जिस वाक्य रचना का उपयोग कर रहा हूं वह काफी मेल नहीं खाता है कि इसका उपयोग rxjs में कैसे किया जाएगा, लेकिन ऐसा इसलिए है क्योंकि नकल करने के लिए अधिक पूर्ण कार्यान्वयन की आवश्यकता होगी। वैसे भी, आपका ध्यान आकर्षित करने वाली मुख्य बात यह है कि हम कार्यों की एक श्रृंखला तैयार करना शुरू कर रहे हैं:

जब मैं .subscribe को कॉल करता हूं, तो वह subscribeToTake को कॉल करता है। यह एक काउंटर सेट करता है, और उसके बाद अन्य ऑब्जर्वेबल.सब्सक्राइब को कॉल करता है, जो सब्सक्राइब टॉइवेंट है। subscribeToEvent तब document.addEventListener को कॉल करता है।

टेक का काम इस फंक्शन चेन के बीच में बैठना है। यह ट्रैक करता है कि अब तक कितने मूल्य उत्सर्जित हुए हैं। यदि गिनती काफी कम है, तो यह केवल मूल्यों को आगे बढ़ाता है। लेकिन एक बार गिनती पूरी हो जाने के बाद, यह पूर्ण कॉल करेगा, इस प्रकार देखने योग्य समाप्त हो जाएगा। पूर्ण कॉल करने से देखने योग्य किसी भी टियरडाउन तर्क को चलाने का कारण बनता है, या इसकी श्रृंखला में कुछ भी होता है। take के लिए कोई टियरडाउन लॉजिक नहीं है, लेकिन fromEvent इवेंट श्रोता को हटाने के लिए कुछ टियरडाउन लॉजिक चलाएगा।

5
Nicholas Tower 9 सितंबर 2019, 19:05