RxJava Meditation Record (a): Do you think RxJava really good?

Source: Internet
Author: User
Tags stream api throwable java 8 stream

I first contact RxJava two years ago, like most beginners, see the first RxJava primer article is the "RxJava to Android developers", this article spread widely, I believe that almost all of the learning RxJava developers have read. Although the article targeted the reader is RxJava beginners, but after reading still feel mengmengdongdong, total feeling still not very understanding the framework design concept and advantages.

Then there is the opportunity to use RxJava to reconstruct the project's network request and cache layer, while the data access layer and other functional modules in the project have been reconstructed, and we have chosen to use the RxJava, without exception.
Recently looked at some technical articles, found that involving RxJava articles or mostly to get started, I try to read from a beginner's point of view, found that many articles did not talk about the key concept points, cite examples are not appropriate. Recall two years ago just learned RxJava, although read a lot of RxJava introductory article, but always can not understand RxJava exactly where, so must be where the problem. So with this rethinking, I hope to rethink RxJava with you and rethink whether RxJava really makes our development easier.
Is the observer pattern so magical?
Almost all RxJava introductory introduction, will use a certain amount of space to introduce the "observer pattern", tells you that the observer pattern is the core of RxJava, is the cornerstone:
Observable.subscribe (New observer<string> () {br/> @Override

LOG.D (Tag, "Item:" + s);
}

@Overridepublic void onCompleted() {    Log.d(tag, "Completed!");}@Overridepublic void onError(Throwable e) {    Log.d(tag, "Error!");}

})
Copy code Young I do not know how to feel li: "Good, this is the Observer mode," but the heart still feel something wrong: "This code is not a bit ugly?" The callback name that received the data is actually called OnNext? ”
But in fact, the observer is not a new concept, even if you are a novice, you must have written a lot of observer pattern code, you can read the following line of code to show that you have the observer pattern in the chest:
Button.setonclicklistener (V-dosomething ());
Copy code This is the Observer pattern, Onclicklistener subscribe to the button's click event, it's that simple. The original writing comparison above RxJava that long string of writing, is not much simpler. One might say that RxJava can also be written as a line:
Rxview.clicks (Button). Subscribe (v-dosomething ());
Copy code don't say that. Need to introduce rxbinding this third-party library, regardless of this, these two writing at most is only a tie, fully reflects the RxJava have any advantage.
That's the first argument I'm going to make, if it's just to use the RxJava observer pattern, and instead of Callback the original form to RxJava's Observable subscription pattern, you just rewrite one observer pattern into another observer pattern. I am a pragmatist and use RxJava not for dazzle, so is the observer pattern the reason we use RxJava? Of course not.
Is the chain programming very bad?
Chained programming is also a high-frequency word that comes up every time you mention RxJava, and many people describe chained programming as the "killer" of RxJava to solve asynchronous tasks:
Observable.from (folders)
. FlatMap (FUNC1) (folder), {Observable.from (File.listfiles ())})
. Filter ((FUNC1) (file), {file.getname (). EndsWith (". png")})
. Map (Func1) (file), {getbitmapfromfile (file)})
. Subscribeon (Schedulers.io ())
. Observeon (Androidschedulers.mainthread ())
. Subscribe ((Action1) (bitmap), {imagecollectorview.addimage (bitmap)});
This code of copying code appears very often, as if it were the best evidence of the benefits of RxJava's chained programming. But to be fair, when I see this example, my heart is calm, and there is no psychological activity in my heart that "it is long but clear" as most articles write.
First of all, FLATMAP, filter, map these operators, for beginners without functional programming experience, not good understanding. Second, although this code uses a lot of RxJava operators, but its logical nature is not complicated, that is, in the background thread to a folder inside the PNG end of the image file parsing, to the UI thread to render.
The above code, also with a counter example, uses the new Thread () to implement the version:
New Thread () {br/> @Override
Super.run ();
for (File folder:folders) {
file[] files = folder.listfiles ();
for (File file:files) {
if (File.getname (). EndsWith (". png")) {
Final Bitmap Bitmap = getbitmapfromfile (file);
Getactivity (). Runonuithread (New Runnable () {br/> @Override
Imagecollectorview.addimage (bitmap);
}
});
}
}
}
}
}.start ();
Copy the code comparison two ways, you can find that the RxJava version of the indentation is reduced, because it takes advantage of the function of the operator, the original nested for loop logic flattened to the same level, in fact, we can also put the above example of the nested logic flat, since to use lambda expression, It would be fair to have everyone use it:
New Thread ((), {
file[] pngfiles = new file[]{};
for (File folder:folders) {
Pngfiles = Arrayutils.addall (Pngfiles, Folder.listfiles ());
}
for (File file:pngfiles) {
if (File.getname (). EndsWith (". png")) {
Final Bitmap Bitmap = getbitmapfromfile (file);
Getactivity (). Runonuithread ((), Imagecollectorview.addimage (bitmap));
}
}
}). Start ();
Copy code Frankly, this code has nothing to do except the new Thread (). Start () There is no big problem outside the slot. The RxJava version does have fewer code, and eliminates an intermediate variable pngfiles, thanks to the API of functional programming, but in real-world development, there is no big gap between performance and project maintainability, even if the team is not familiar with functional programming, The latter is easier to accept.
Back to "chained programming" just now, RxJava the Java 8 Stream functional programming style supported by Android SDK 24 or more to bring to the lower version of the Android system, it does bring us some convenience, but that's all? So far I have not seen RxJava's special means of handling events, especially asynchronous events.
To be exact, my focus is not on the "chained programming" that most articles preach, and it's not new to translate multiple invocations of asynchronous operations in turn into top-down execution like synchronous code calls, and for this specific example, using Android native Asynctask Or Handler can meet the needs, RxJava compared to the original writing can not reflect its advantages.
In addition, for handling asynchronous tasks, there is the Promise genre, which uses APIs like this:
Promise
. Then (R1-Task1 (R1))
. Then (R2-Task2 (R2))
. Then (R3-TASK3 (R3))
...
Isn't copying code more concise and intuitive than RxJava? And there is no need to introduce functional programming content. This kind of writing, and so-called "logic concise" also have nothing to do, so from now on, RxJava in my mind is just a "Oh, pretty good" framework, but not amazing to me.
This is the second argument that I want to say, the form of chain programming is just a kind of syntax sugar, through the function of the operator can flatten the nesting logic, through other methods can also be nested logic flattened, this is just normal operation, there are other frameworks can achieve similar effects.
RxJava equals async and simplicity?
I believe that the developers who have read the introductory article RxJava "RxJava detailed for Android developers" must be impressed by the two headings in the text:

What the hell is RxJava? --One word: Async

Where's RxJava? --One word: concise

First of all, thank you for throwing the line, very attentively for beginners to prepare this simple and simple introductory article. But I still want to point out that this expression is not rigorous.
Although most of the scenarios in which we use RxJava are related to Asynchrony, the framework is not equivalent to async. To give a simple example:
Observable.just (Subscribe) (System.out::p rintln);
The code above the copy code is executed synchronously, and is not related to async. In fact, the RxJava code is executed synchronously unless you explicitly switch to another Scheduler, or if some of the operations you use implicitly specify other Scheduler RxJava.
This design is related to the ambitions of this framework, and RxJava is a new event-driven programming paradigm that attempts to unified a synchronous and asynchronous world with asynchronous entry points.
As mentioned earlier in this article:

RxJava brings the Java 8 Stream functional programming style supported by the current Android SDK above 24 to the low-version Android system.

So as long as you want, you can use RxJava in your daily synchronous programming, as if you were using the Java 8 Stream API. (But the two are not equivalent because RxJava is event-driven programming)
If you put the routine synchronization programming, encapsulated as synchronous event Observable, then you will find that both synchronous and asynchronous situations are RxJava unified, both have the same interface, can be treated without discrimination, the collaboration between synchronous and asynchronous can also become easier than before.
So, so far, I have concluded here that RxJava is not equal to async.
So RxJava equals brevity? I believe some people will say "Yes, RxJava is very concise", and some people will say "No, RxJava is too bad, not a bit succinct". I can understand both of these statements, but the essence of the problem is the definition of brevity. There will be a section devoted to this question, but I would like to make a conclusion ahead of time that for most people, RxJava is not just about brevity, sometimes even more difficult to understand code and less maintainability of the project.
RxJava is used to solve the Callback Hell?
Many of RxJava's introductory texts proclaim that RxJava is used to solve the problem of Callback Hell (some translated as "callback Hell"), referring to the difficult-to-read state of code rendered by excessive asynchronous invocation nesting.
I don't agree with that. Callback Hell This problem, the most serious disaster area in the Web domain, is one of the most common problems of using JavaScript, so that there is a website callbackhell.com to discuss this issue, due to client programming and WEB Front-end programming has a certain similarity, and Android programming is more or less the problem.
In the above Web site, there are several common ways to circumvent Callback Hell, nothing more than to move nested hierarchies into outer space, instead of using anonymous callback functions to name each callback function. In the case of Java, avoid using anonymous inner classes, assigning an object name to each inner class object. Of course, the framework can also be used to solve such problems, using a framework like Promise, specifically for asynchronous programming, there are similar open source version jdeferred on the Android platform.
In my opinion, a framework like that of jdeferred is more of a purely framework for solving Callback Hell. As for RxJava, mentioned before, it is a more ambitious framework, the correct use of RxJava words, there is really no Callback Hell again, but if RxJava is to solve Callback Hell, it is a bit of anti-aircraft fighting mosquito means.
How to understand RxJava
Perhaps after reading the previous sections, your heart will be like the one I once had, with some negative thoughts about RxJava and a question: what is the meaning of RxJava existence?
Here are a few common examples:

To set the click callback method for the View:

Btn.setonclicklistener (New Onclicklistener () {br/> @Override

Callback Body
}
});
Copy Code
Service Component Binding Operations:

Private Serviceconnection mconnection = new Serviceconnection () {br/> @Override

Callback Bodybr/>}
@Override

Callback Body
}
};

...
Bindservice (Intent, mconnection, context.bind_auto_create);
Copy Code
To initiate a network request using Retrofit:

Call<list<photo>> call = Service.getallphotos ();
Call.enqueue (New callback<list<photo>> () {br/> @Override

Callback Bodybr/>}
@Override

Callback Body
}
});
Copy code in daily development we are facing similar callback functions all the times, and it is easy to see that the most essential function of the callback function is to return the results of the asynchronous call to us, and the rest is similar. So can we not memorize all kinds of callback functions and use only one callback? If we define a unified callback as follows:
public class Callback<t> {
public void Onresult (T result);
}
Copy the code so in 3 cases, the corresponding callback becomes:

Set the callback for the View to the callback<view> of the Click event
The callback for the Service component binding operation is Callback<pair<compnentname, ibinder>> (onserviceconnected), callback< Compnentname> (onservicedisconnected)
The callback for initiating a network request using Retrofit is callback<list<photo>> (onresponse), callback<throwable> (onfailure)

As long as we follow this line of thinking, we can encapsulate all the asynchronous callbacks into the Callback<t> form, and we no longer need to memorize different callbacks, just need to interact with a callback.
Writing here, you should have understood that the first and most basic meaning of RxJava is to unify the callback interfaces of all asynchronous tasks. And this interface is OBSERVABLE<T>, this and just callback<t> is actually a meaning. In addition, we can consider making this callback a bit more general--can be called back multiple times, corresponding, Observable represents an event stream, it can emit a series of events (OnNext), including a termination signal (OnComplete).
If RxJava only unified the callback, there is nothing remarkable about it. The unification of callbacks, in addition to satisfying obsessive-compulsive disorder, has limited additional benefits and the need to transform existing code, which in the short term is a negative income. But Observable belongs to RxJava infrastructure, with Observable after the RxJava just inserted the wings of imagination.

RxJava Meditation Record (a): Do you think RxJava really good?

Contact Us

The content source of this page is from Internet, which doesn't represent Alibaba Cloud's opinion; products and services mentioned on that page don't have any relationship with Alibaba Cloud. If the content of the page makes you feel confusing, please write us an email, we will handle the problem within 5 days after receiving your email.

If you find any instances of plagiarism from the community, please send an email to: info-contact@alibabacloud.com and provide relevant evidence. A staff member will contact you within 5 working days.

A Free Trial That Lets You Build Big!

Start building with 50+ products and up to 12 months usage for Elastic Compute Service

  • Sales Support

    1 on 1 presale consultation

  • After-Sales Support

    24/7 Technical Support 6 Free Tickets per Quarter Faster Response

  • Alibaba Cloud offers highly flexible support services tailored to meet your exact needs.