RxJava provides support for transforming the sequence of events, so-called transformations, that is, the object in the sequence of events or the entire sequence is processed, converted into different events or sequence of events.
Not only for event objects, but also for the entire event queue.
The transformation is mainly from the "RxJava to Android Developers"
1.
Event Object Transform-map ()
map(): the direct transformation of the event object; RxJava The most commonly used transforms, which can be Observable in-depth objects 1 Convert to Object 2 sent to Subscriber .
The basic usage is as follows:
Observable.just (R.DRAWABLE.T) . Map (new Func1<integer, drawable> () { @Override Public drawable call (integer integer) { Return Getresources (). getdrawable (integer); } }) . Subscribe (New action1<drawable> () { @Override public void Call (Drawable drawable) { Showimg (drawable); } }); |
2. Event Sequence Transformation-flatmap ()
FlatMap () is also the same as map (), which converts the passed parameters back to another object, and unlike map (), FlatMap () returns a Observable object, and the Observable object is not sent directly to the Su Bscriber in the callback method.
The principle of FlatMap ():
1. Create an Observable object using the incoming event object;
2. Do not send this Observable, but activate it, so it starts sending events;
3. Every event sent by the created Observable is remitted to the same Observable, and this Observable is responsible for unifying the events to Subscriber's callback method.
In these three steps, the event was split into level two and distributed through a unified path after the initial object was "flattened" by a newly created set of Observable.
//
Extensions: Because asynchronous code can be added to nested observable, FlatMap () is also commonly used for nested asynchronous operations, such as nested network requests.
The basic usage of flatmap () is to define a book type, including a name and a list of chapters , and print out a list of all chapters by Flatmap () .
? Book.java
public class Book { public String name; Public list<string> chapterlist = new arraylist<string> ();
public void Addchapter (String chapter) { Chapterlist.add (chapter); } } |
? Flagmap () use
book[] Books = getbooklist (5); Observable.from (Books) . FLATMAP (New Func1<book, observable<string>> () { @Override Public observable<string> Call (book book) { Return Observable.from (book.chapterlist); } }) . Subscribe (New action1<string> () { @Override public void Call (String s) { LOG.V (TAG, s); } }); |
3. Principle of Transformation: lift ()
All transformations may be different, essentially handling and resending the sequence of events. Within the RxJava, they are based on the same fundamental transformation method: Lift (Operator).
Lift () Realization of the source code:
/** * Lifts a function to the current Observable and returns a new Observable then subscribed to would pass * The values of the current Observable through the Operator function. * <p> * In other words, this allows chaining observers together on a Observable for acting on the values within * The Observable. * <p> {@code * OBSERVABLE.MAP (...). Filter (...). Take (5). Lift (new Operatora ()). Lift (new Operatorb (...)). Subscribe () * } * <p> * If the operator creating is designed to act on the individual items emitted by a source * Observable, use {@code lift}. If your operator is designed to transform the source Observable as a whole * (for instance, by applying a particular set of existing RxJava operators to it) use {@link #compose}. * <dl> * <dt><b>Scheduler:</b></dt> * <dd>{@code Lift} does not operate by default on a particular {@link scheduler}.</dd> * </dl> * * @param operator The operator that implements the Observable-operating function to being applied to the source * Observable * @return An Observable that's the result of applying the lifted Operator to the source Observable * @see <a href= "https://github.com/ReactiveX/RxJava/wiki/Implementing-Your-Own-Operators" >rxjava wiki: Implementing Your Own Operators</a> */ Public final <R> observable<r> lift (final operator<? extends R,? Super T> Operator) { return new observable<r> (new onsubscribe<r> () { @Override public void call (SUBSCRIBER<? Super r> O) { try { subscriber<? Super T> st = Hook.onlift (operator). Call (O); try { New subscriber created and being subscribed with so ' onStart ' it St.onstart (); Onsubscribe.call (ST); } catch (Throwable e) { Localized capture of errors rather than it skipping all operators and ending up in the try/catch of the Subscribe method which then Prevents onerrorresumenext and other similar approaches to error handling Exceptions.throwiffatal (e); St.onerror (e); } } catch (Throwable e) { Exceptions.throwiffatal (e); If the lift function failed all we can do are pass the error to the final subscriber As we don ' t has the operator available to us O.onerror (e); } } }); } |
Through the lift () source, a new observable is generated, and a new subscriber is created in the call () callback method of the new observable (newly) onsubscribe. , the new Subscriber (the final target) uses the proxy of the subscriber that was eventually called, and then uses the original observable (old) Onsubscribe to invoke the new Subscriber.
Figure lift () transformation process-(image from "RxJava to Android Developer")
lift() ImplementProcess
1) lift () Create a new Observable, at this time with the original Observable, there are already two Observable;
2) in the same way, the new onsubscribe in the new Observable plus the original onsubscribe in the original Observable, there are two onsubscribe;
3) When the user calls the Observable subscribe () after lift (), the new Observable returned by lift () is used, and the Onsubscribe.call (subscriber) that it triggers is also used New Onsubscribe in the new Observable, that is, the onsubscribe generated in lift ();
4) and this new Onsubscribe call () method of Onsubscribe, refers to the original Observable in the original onsubscribe, in this call () method, the new Onsubscribe use Operato R.call (subscriber) generates a new Subscriber (Operator is where the new Subscriber is associated with the original subscriber through its own call () method and inserts its own "transform" Code to implement the transformation), and then use this new Subscriber to subscribe to the original Observable.
The lift () process, a bit like a proxy mechanism, implements the transformation of event sequences through event interception and processing.
After Observable executes the lift (Operator) method, a new Observable is returned, which, like a proxy, is responsible for receiving the original Observable event and sending it to Subscriber.
4. Custom Observable.operator, call lift () directly
The following example implements the same functionality as the previous FlatMap () implementation:
Observable.from (Getbooklist (4)) . Lift (New observable.operator<string, book> () { @Override Public subscriber<? Super Book> call (Final subscriber<? Super String> Subscriber) { return new subscriber<book> () { @Override public void oncompleted () { Subscriber.oncompleted (); }
@Override public void OnError (Throwable e) { Subscriber.onerror (e); }
@Override public void OnNext (book book) { for (String chapter:book.chapterList) { Subscriber.onnext (chapter); } } }; } }) . Subscribe (New action1<string> () { @Override public void Call (String s) { LOG.V (TAG, s); } }); |
5. Compose (Transformer) transform
Compose (Transformer) transform for observable itself. Assuming that there are multiple Observable in the program, and that they all need to apply a set of identical lift () transformations, they can be processed using the Compose method instead of each calling the same transformation process
Instance code, if you need to convert the book to the corresponding chapters, two observable have different ways of handling the chapter data:
Final Observable.transformer Bookttransformer = new Observable.transformer<book, string> () { @Override Public observable<string> Call (observable<book> bookobservable) { Return Bookobservable.flatmap (New Func1<book, observable<string>> () { @Override Public observable<string> Call (book book) { Return Observable.from (book.chapterlist); } }); } };
Observable.from (Getbooklist (4)) . Compose (Bookttransformer) . Subscribe (New action1<string> () { @Override public void Call (String s) { Handling Mode 1 LOG.V (TAG, s); } });
//// Observable.from (Getbooklist (2)) . Compose (Bookttransformer) . Subscribe (New action1<string> () { @Override public void Call (String s) { Handling Mode 2 LOG.V (TAG, s); } }); |
Rxjava using (iv) transform