दिलचस्प पोस्ट
JqGrid स्तंभ वरीयताओं को जारी रखने के लिए रेल की स्थापना उबंटू पर विफल रही है "ऐसी फाइल लोड नहीं कर सकती – एमकेएमएफ" अन्य स्रोत के लिए पायथन खोज पथ का विस्तार करें वक्रार (अधिकतम) हर जगह? अजगर के साथ एक सरणी को शफल करें, अजगर के साथ सरणी आइटम ऑर्डर को यादृच्छिक बनाएं CUDA: कुल में कितने समवर्ती धागे हैं? एंड्रॉइड – विस्तार योग्यलिस्टव्यू event.preventDefault () बनाम वापसी झूठी एक देशी विधि को बुलाते समय एक जीवीएम क्या करता है? सीएसएस: एक <div> तत्व के भीतर केंद्र तत्व NSString की भाषा का पता लगाएं सर्वर-साइड में फिल्मों को चित्रित करने के लिए AWT और स्विंग का उपयोग करने वाला जावा ऐप को पोर्ट करना कैसे MATLAB में बार 3 साजिश में शून्य मानों को छिपाने के लिए क्या टीसीपी और यूडीपी सॉकेट समान पोर्ट का उपयोग कर सकते हैं? एपाचे को 80 से अधिक पोर्ट पर सुनने के लिए कॉन्फ़िगर करें

आप आरएक्सजेवा में मानचित्र बनाम फ्लैटमैप कब उपयोग करते हैं?

आप आरएक्सजेवा में मानचित्र बनाम फ्लैटमैप कब उपयोग करते हैं?

उदाहरण के लिए कहें, हम JSON वाले फाइलों को मैप करना चाहते हैं जिसमें स्ट्रिंग्स में स्ट्रिंग होते हैं जिसमें JSON-

नक्शा का उपयोग करके, हमें अपवाद से किसी तरह से निपटना होगा। पर कैसे?:

Observable.from(jsonFile).map(new Func1<File, String>() { @Override public String call(File file) { try { return new Gson().toJson(new FileReader(file), Object.class); } catch (FileNotFoundException e) { // So Exception. What to do ? } return null; // Not good :( } }); 

फ्लैटमैप का उपयोग करना, यह बहुत अधिक शब्दबोध है, लेकिन हम समस्या को ऑब्ज़र्वबेस की श्रृंखला से आगे बढ़ा सकते हैं और त्रुटि को संभाल सकते हैं यदि हम कहीं और चुनते हैं और फिर से प्रयास करें:

 Observable.from(jsonFile).flatMap(new Func1<File, Observable<String>>() { @Override public Observable<String> call(final File file) { return Observable.create(new Observable.OnSubscribe<String>() { @Override public void call(Subscriber<? super String> subscriber) { try { String json = new Gson().toJson(new FileReader(file), Object.class); subscriber.onNext(json); subscriber.onCompleted(); } catch (FileNotFoundException e) { subscriber.onError(e); } } }); } }); 

मुझे मानचित्र की सादगी पसंद है, लेकिन फ्लैटमैप की त्रुटि संभालना (वर्बोसिस नहीं)। इस फ्लोटिंग के आसपास मैंने किसी भी सर्वोत्तम अभ्यास को नहीं देखा है और मुझे उत्सुक है कि व्यवहार में इसका इस्तेमाल कैसे किया जा रहा है

Solutions Collecting From Web of "आप आरएक्सजेवा में मानचित्र बनाम फ्लैटमैप कब उपयोग करते हैं?"

map एक घटना को दूसरे में बदल देती है flatMap एक घटना को शून्य या अधिक ईवेंट में flatMap । (यह इंट्रोटोआरएक्स से लिया गया है)

जैसा कि आप अपने जेसन को ऑब्जेक्ट में बदलना चाहते हैं, नक्शे का उपयोग करना पर्याप्त होना चाहिए।

FileNotFoundException से निपटना एक और समस्या है (मानचित्र या फ्लैटमैप का उपयोग करके इस समस्या का समाधान नहीं होगा)।

अपनी अपवाद समस्या को हल करने के लिए, इसे केवल एक गैर-चेक अपवाद के साथ फेंक दें: RX आपके लिए ऑनरर हैंडलर को कॉल करेगा।

 Observable.from(jsonFile).map(new Func1<File, String>() { @Override public String call(File file) { try { return new Gson().toJson(new FileReader(file), Object.class); } catch (FileNotFoundException e) { // this exception is a part of rx-java throw OnErrorThrowable.addValueAsLastCause(e, file); } } }); 

फ्लैटमैप के साथ सटीक समान संस्करण:

 Observable.from(jsonFile).flatMap(new Func1<File, Observable<String>>() { @Override public Observable<String> call(File file) { try { return Observable.just(new Gson().toJson(new FileReader(file), Object.class)); } catch (FileNotFoundException e) { // this static method is a part of rx-java. It will return an exception which is associated to the value. throw OnErrorThrowable.addValueAsLastCause(e, file); // alternatively, you can return Obersable.empty(); instead of throwing exception } } }); 

आप फ्लैट मैप संस्करण में भी एक नया ऑब्ज़र्व्यूबल लौट सकते हैं जो सिर्फ एक त्रुटि है।

 Observable.from(jsonFile).flatMap(new Func1<File, Observable<String>>() { @Override public Observable<String> call(File file) { try { return Observable.just(new Gson().toJson(new FileReader(file), Object.class)); } catch (FileNotFoundException e) { return Observable.error(OnErrorThrowable.addValueAsLastCause(e, file)); } } }); 

FlatMap मानचित्र की तरह बहुत व्यवहार करता है, अंतर यह है कि यह एक खुद को अवलोकन देता है, इसलिए यह अतुल्यकालिक कार्यों पर नक्शा करने के लिए बिल्कुल उपयुक्त है। मानचित्र को स्रोत के रूप में एक ही प्रकार की वस्तुओं का उत्सर्जन नहीं करना पड़ता है।

व्यावहारिक रूप से, नक्शा सिर्फ जंजीर की प्रतिक्रिया पर एक परिवर्तन करता है (कोई अवलोकन नहीं किया जा रहा); जबकि FlatMap एक Observable<T> , यही कारण है कि FlatMap की सिफारिश की गई है यदि आप विधि के अंदर एक अतुल्यकालिक कॉल करने की योजना बना रहे हैं, तो:

  • नक्शा प्रकार का एक वस्तु टी देता है
  • FlatMap एक Observable<T>

एक स्पष्ट उदाहरण यहां देखा जा सकता है: http://blog.couchbase.com/why-couchbase-chose-rxjava-new-java-sdk

काउचबेस जावा 2.x क्लाइंट आरसीए का उपयोग करता है ताकि एक सुविधाजनक तरीके से एसिंक्रोनस कॉल उपलब्ध हो सके। चूंकि यह आरएक्स का उपयोग करता है, इसमें तरीकों का नक्शा और फ्लैटमैप है, उनके दस्तावेज़ीकरण में स्पष्टीकरण सामान्य अवधारणा को समझने में सहायक हो सकता है।

त्रुटियों को संभालने के लिए, अपने संदिग्धकर्ता पर त्रुटि को ओवरराइड करें।

 Subscriber<String> mySubscriber = new Subscriber<String>() { @Override public void onNext(String s) { System.out.println(s); } @Override public void onCompleted() { } @Override public void onError(Throwable e) { } }; 

यह इस दस्तावेज़ को देखने में मदद कर सकता है: http://blog.danlew.net/2014/09/15/grokking-rxjava-part-1/

आरएक्स के साथ त्रुटियों का प्रबंधन करने के बारे में एक अच्छा स्रोत पाया जा सकता है: https://gist.github.com/daschl/db9fcc9d2b932115b679

आपके मामले में मुझे लगता है कि आपको मानचित्र की आवश्यकता है, क्योंकि केवल 1 इनपुट और 1 आउटपुट है।

नक्शा – आपूर्ति की गई सुविधा केवल एक आइटम को स्वीकार करती है और वह आइटम लौटाता है जो आगे (केवल एक बार) उत्सर्जित हो जाएगी

फ्लैटमैप – आपूर्ति की गई वस्तु एक वस्तु को स्वीकार करती है तो एक "अवलोकन" देता है, जिसका अर्थ है कि नए "निरीक्षण" के प्रत्येक आइटम को अलग-अलग उत्सर्जित किया जाएगा।

हो सकता है कोड आपके लिए चीजों को साफ करेगा।

  //START DIFFERENCE BETWEEN MAP AND FLATMAP Observable.just("item1") .map( str -> { System.out.println("inside the map " + str); return str; }) .subscribe(System.out::println); Observable.just("item2") .flatMap( str -> { System.out.println("inside the flatMap " + str); return Observable.just(str + "+", str + "++" , str + "+++"); }) .subscribe(System.out::println); //END DIFFERENCE BETWEEN MAP AND FLATMAP 

आउटपुट:

 inside the map item1 item1 inside the flatMap item2 item2+ item2++ item2+++ 

जिस तरह से मैं इसके बारे में सोचता हूं, वह है कि आप flatMap उपयोग flatMap जब आप map() अंदर flatMap करना चाहते हैं, तो एक Observable रिटर्न देता है उस स्थिति में आप अभी भी map() का उपयोग करने की कोशिश कर सकते हैं, लेकिन यह अप्रभावी होगा मुझे क्यों समझाने की कोशिश करते हैं

यदि इस स्थिति में आप map साथ छड़ी करने का फैसला किया है, तो आपको एक Observable<Observable<Something>> उदाहरण के लिए, यदि हम एक काल्पनिक RxGson लाइब्रेरी का इस्तेमाल करते हैं, जिसने एक Observable<String> से इसे toJson() विधि (केवल एक String लौटने के बजाय) लौटाया है तो यह इस प्रकार दिखाई देगा:

 Observable.from(jsonFile).map(new Func1<File, Observable<String>>() { @Override public Observable<String>> call(File file) { return new RxGson().toJson(new FileReader(file), Object.class); } }); // you get Observable<Observable<String>> here 

इस बिंदु पर यह इस तरह के एक अवलोकन करने योग्य subscribe() लिए बहुत मुश्किल होगा इसके अंदर आपको एक Observable<String> subscribe() मिलेगा जिसमें आपको मूल्य प्राप्त करने के लिए फिर से subscribe() आवश्यकता होगी। जो व्यावहारिक या देखने के लिए अच्छा नहीं है।

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

तो हमारे पिछले स्निपेट में संशोधन होगा जो हम प्राप्त करेंगे:

 Observable.from(jsonFile).map(new Func1<File, Observable<String>>() { @Override public Observable<String>> call(File file) { return new RxGson().toJson(new FileReader(file), Object.class); } }).merge(); // you get Observable<String> here 

यह बहुत अधिक उपयोगी है, क्योंकि उस (या मैपिंग, या फ़िल्टरिंग, या …) की सदस्यता लेने के लिए आपको String वैल्यू मिलता है। (इसके अलावा, आप को याद रखें, इस तरह के merge() को आरजेक्सवा में मौजूद नहीं है, लेकिन यदि आप मर्ज के विचार को समझते हैं, तो मुझे आशा है कि आप यह भी समझ पाएंगे कि यह कैसे काम करेगा।)

तो मूल रूप से इसलिए क्योंकि इस तरह के merge() को शायद कभी भी उपयोगी हो सकता है जब वह एक map() एक अवलोकन में वापस ले जाता है और इसलिए आपको इसे फिर से लिखना नहीं पड़ता है, flatMap() को flatMap() के रूप में बनाया गया था यह मैपिंग फ़ंक्शन को एक सामान्य map() रूप में लागू करता है, लेकिन बाद में बदले गए मूल्यों को निकालने के बजाय यह "फ़्लैटेंस" (या विलय) करता है

यही सामान्य उपयोग का मामला है यह कोडबेस में सबसे उपयोगी होता है जो जगह पर आरएक्स का उपयोग करता है और आपको अवलोकन में कई तरीके मिलते हैं, जो आप अवलोकन में लौटने वाले अन्य तरीकों के साथ श्रृंखला करना चाहते हैं।

आपके उपयोग के मामले में यह उपयोगी भी होता है, क्योंकि map() केवल onNext() पर उत्सर्जित एक मूल्य को onNext() में उत्सर्जित अन्य मान में onNext() । लेकिन यह इसे कई मूल्यों में परिवर्तित नहीं कर सकता, कोई भी मूल्य या त्रुटि नहीं। और जैसा कि अकाराणोक ने अपने जवाब में लिखा था (और मन में आप मुझ से बहुत चालाक है, शायद सामान्य तौर पर, लेकिन कम से कम जब यह आरजेक्सवा की बात आती है) तो आपको अपने map() से अपवाद नहीं फेंकना चाहिए। इसके बजाय आप flatMap() उपयोग कर सकते हैं और

 return Observable.just(value); 

जब सब ठीक हो जाता है, लेकिन

 return Observable.error(exception); 

जब कुछ विफल रहता है
एक पूर्ण स्निपेट के लिए उसका उत्तर देखें: https://stackoverflow.com/a/30330772/1402641

मैं सिर्फ flatMap साथ जोड़ना चाहता था, आपको वास्तव में फ़ंक्शन के अंदर अपने स्वयं के कस्टम निरीक्षणालय का उपयोग करने की आवश्यकता नहीं है और आप मानक कारखाने के तरीकों / ऑपरेटरों पर भरोसा कर सकते हैं:

 Observable.from(jsonFile).flatMap(new Func1<File, Observable<String>>() { @Override public Observable<String> call(final File file) { try { String json = new Gson().toJson(new FileReader(file), Object.class); return Observable.just(json); } catch (FileNotFoundException ex) { return Observable.<String>error(ex); } } }); 

आम तौर पर, यदि आपको संभव हो तो XXX तरीकों और कॉलबैक पर से (रनटाइम) अपवाद फेंकने से बचना चाहिए, भले ही हमने आरएक्सजेवा में हम जितने सुरक्षा उपायों को बनाए रखा हो।

यहां एक सरल अंगूठे-नियम है, जिसका उपयोग मैं आरएक्स के Observable में map() पर flatMap() का उपयोग करने के बारे में निर्णय लेने में सहायता के लिए करता हूं।

एक बार जब आप कोई निर्णय लेते हैं कि आप एक map परिवर्तन को लागू करने जा रहे हैं, तो आप कुछ ऑब्जेक्ट सही करने के लिए अपना रूपांतरण कोड लिखना चाहते हैं?

यदि आप अपने परिवर्तन के अंतिम परिणाम के रूप में लौट रहे हैं:

  • एक नॉन-ऑब्जेक्टिव ऑब्जेक्ट तो आप बस map() उपयोग map() और map() उस ऑब्जेक्ट को ऑब्ज़ेबल में लपेटता है और इसका उत्सर्जन करता है।

  • एक Observable वस्तु, तो आप flatMap() उपयोग करें और flatMap() Observable flatMap() को लपेटता है, लौटा हुआ ऑब्जेक्ट उठाता है, इसे अपने स्वयं के अवलोकन के साथ लपेटता है और इसे बाहर flatMap() है।

उदाहरण के लिए कहें कि हमारे पास एक विधि शीर्षक कैस (स्ट्रिंग इनपुटपाराम) है जो इनपुट परम के शीर्षक वाली कैश्ड स्ट्रिंग ऑब्जेक्ट देता है। इस विधि का वापसी प्रकार String या Observable<String> किया जा सकता है Observable<String>

  • अगर वापसी का titleCase(..) केवल String होना था, तो आप map(s -> titleCase(s))

  • यदि रिटर्न टाइप titleCase(..) को Observable<String> , तो आप flatMap(s -> titleCase(s))

उम्मीद है कि स्पष्ट है

उस परिदृश्य में नक्शा का उपयोग करें, आपको इसके लिए एक नया अवलोकन आवश्यक नहीं है।

आपको अपवाद का प्रयोग करना चाहिए। प्रॉपैगेट, जो एक आवरण है ताकि आप आरएक्स तंत्र के उन चेक अपवाद को भेज सकें

 Observable<String> obs = Observable.from(jsonFile).map(new Func1<File, String>() { @Override public String call(File file) { try { return new Gson().toJson(new FileReader(file), Object.class); } catch (FileNotFoundException e) { throw Exceptions.propagate(t); /will propagate it as error } } }); 

इसके बाद आपको ग्राहक में इस त्रुटि को संभालना चाहिए

 obs.subscribe(new Subscriber<String>() { @Override public void onNext(String s) { //valid result } @Override public void onCompleted() { } @Override public void onError(Throwable e) { //e might be the FileNotFoundException you got } };); 

इसके लिए एक उत्कृष्ट पोस्ट है: http://blog.danlew.net/2015/12/08/error-handling-in-rxjava/

कुछ मामलों में आप अवलोकन के चेन को समाप्त कर सकते हैं, जिसमें आपका नमूना एक और नमूना वापस लौटा देगा। 'फ्लैटमैप' की तरह दूसरे दृश्य को खोलता है जिसे पहले एक में दफन किया गया है और आपको सीधे अन्य आंकड़ों तक पहुंचना पड़ता है जब सदस्यता लेने के दौरान बाहर निकल पड़ता है।