I got slightly confused about the differences between Handlers
, AsyncTask
and Threads
in Android. I've read quite a few blogs and questions here in stackoverflow.
Handler
are background threads that provide you to communicate with the UI. Updating a progressbar for instance should be done via Handler
. Using Handlers you have the advantage of MessagingQueues
, so if you want to schedule messages or update multiple UI elements or have repeating tasks.
AsyncTask
are similar, infact they make use of Handler
, but doesn't run in the UI thread, so it's good for fetching data, for instance fetching web services. Later you can interact with the UI.
Thread
however can't interact with the UI, provide more "basic" threading and you miss all the abstractions of AsyncTask
.
However I would like to have a socket connection run in a service. Should this be run in a handler or a thread, or even an AsyncTask
? UI interaction is not necessary at all. Does it make a difference in terms of performance which I use?
Meanwhile the documentation has been majorly improved.
If you look at the source code of
AsyncTask
andHandler
, you will see their code is written purely in Java. (Of course, there are some exceptions, but that is not an important point.)So there is no magic in
AsyncTask
orHandler
. They just make your job easier as a developer.For example: If Program A calls method A(), method A() could run in a different thread with Program A.You can easily verify it using:
Why you should use a new thread? You can google for it. Many many reasons.
So, what is the difference between
Thread
,AsyncTask
, andHandler
?AsyncTask
andHandler
are written in Java (internally they use aThread
), so everything you can do withHandler
orAsyncTask
, you can achieve using aThread
too.What can
Handler
andAsyncTask
really help you with?The most obvious reason is communication between the caller thread and the worker thread. (Caller Thread: A thread which calls the Worker Thread to perform some task. A Caller Thread does not necessarily have to be the UI thread). Of course, you can communicate between two threads in other ways, but there are many disadvantages (and dangers) due to thread safety issues.
That is why you should use
Handler
andAsyncTask
. They do most of the work for you, you just need to know what methods to override.The difference between
Handler
andAsyncTask
is: UseAsyncTask
when Caller thread is a UI Thread. This is what android document says:I want to emphasize on two points:
1) Easy use of the UI thread (so, use when caller thread is UI Thread).
2) No need to manipulate handlers. (means: You can use Handler instead of AsyncTask, but AsyncTask is an easier option).
There are many things in this post I haven't said yet, for example: what is UI Thread, or why it's easier. You must know some method behind each kind and use it, you will completely understand why..
@: when you read the Android document, you will see:
They may seem strange at first. Just understand that each thread has each message queue (like a to do list), and the thread will take each message and do it until the message queue is empty (just like you finish your work and go to bed). So, when
Handler
communicates, it just gives a message to caller thread and it will wait to process. Complicated? Just remember thatHandler
can communicate with the caller thread in a safe way.Thread
:You can use new
Thread
for long running background tasks without impacting UI Thread. From java Thread, you can't update UI Thread.Since normal Thread is not much useful for Android architecture, helper classes for threading have been introduced.
You can find answers to your queries in Threading performance documentation page.
Handler:
A
Handler
allows you to send and process Message andRunnable
objects associated with a thread'sMessageQueue
. EachHandler
instance is associated with a single thread and that thread's message queue.There are two main uses for a
Handler
:To schedule messages and runnables to be executed as some point in the future;
To enqueue an action to be performed on a different thread than your own.
AsyncTask:
AsyncTask
enables proper and easy use of the UI thread. This class allows you to perform background operations and publish results on the UI thread without having to manipulate threads and/or handlers.Drawbacks:
By default, an app pushes all of the
AsyncTask
objects it creates into a single thread. Therefore, they execute in serial fashion, and—as with the main thread—an especially long work packet can block the queue. Due to this reason, use AsyncTask to handle work items shorter than 5ms in duration.AsyncTask
objects are also the most common offenders for implicit-reference issues.AsyncTask
objects present risks related to explicit references, as well.HandlerThread:
You may need a more traditional approach to executing a block of work on a longer running thread (unlike AsyncTask, which should be used for 5ms workload) , and some ability to manage that workflow manually. A handler thread is effectively a long-running thread that grabs work from a queue, and operates on it.
ThreadPoolExecutor:
This class manages the creation of a group of threads, sets their priorities, and manages how work is distributed among those threads. As workload increases or decreases, the class spins up or destroys more threads to adjust to the workload.
If workload is more and single
HandlerThread
is not suffice, you can go forThreadPoolExecutor
Since UI interaction is not required, you may not go for
AsyncTask
. Normal threads are not much useful and henceHandlerThread
is best option. Since you have to maintain socket connection, Handler on main thread is not useful at all. Create aHandlerThread
and get aHandler
from looper ofHandlerThread
.If you want to communicate back to UI thread, you can use one more Handler to process response.
in your
Runnable
, you can addMore details about implementation can be found here:
Android: Toast in a thread
Let me try and answer the question here with an example :) - MyImageSearch [Kindly refer the image here of the main activity screen - containing an edit text / search button / grid view]
Description of MyImageSearch - Once user enters the details on the edit text field and clicks on the search button, we will search images on the internet via the web services provided by flickr (you only need to register there to get a key/secret token) - for searching we send an HTTP Request and GET JSON Data back in response containing the url's of individual images which we will then use to load the grid view.
My Implementation - In the main activity I will define a inner class which extends the AsyncTask to send the HTTP Request in doInBackGround Method and fetch the JSON Response and update my local ArrayList of FlickrItems which I am going to use to update my GridView via the FlickrAdapter (extends the BaseAdapter) and call the adapter.notifyDataSetChanged() in the onPostExecute() of AsyncTask to reload the grid view. Note that here the HTTP Request is a blocking call because of which I have done it via the AsyncTask. And, I can cache the items in adapter to increase the performance or store them on SDCard. The grid that I will be inflating in the FlickrAdapter contains in my implementation a progressbar and image view. Below you can find the code for mainActivity which I used.
Answer to the Question Now - So once we have the JSON data for fetching individual Images we can implement the logic of getting the images in background via Handlers or Threads or AsyncTask. We should note here that since my images once downloaded must be displayed on the UI/main thread we cannot simply use threads as it is since they don't have access to the context. In the FlickrAdapter, the choices I could think of:
Here the source code:
I hope my answer though long will help in understanding some of the finer details.
AsyncTask
is designed to perform not more than few seconds operation to be done in background (not recommended for megabytes of file downloading from server or compute cpu intensive task such as file IO operations ). If you need to execute a long running operation, you have been strongly advised to use java native threads. Java gives you various thread related classes to do what you need. UseHandler
to update the UI Thread.As the Tutorial on Android background processing with Handlers, AsyncTask and Loaders on the Vogella site puts it:
The
Handler
class can be used to register to a thread and provides a simple channel to send data to this thread.The
AsyncTask
class encapsulates the creation of a background process and the synchronization with the main thread. It also supports reporting progress of the running tasks.And a
Thread
is basically the core element of multithreading which a developer can use with the following disadvantage:And regarding the
AsyncTask
, as the Android Developer's Reference puts it:Update May 2015: I found an excellent series of lectures covering this topic.
Important: If you are at a point where you are considering to use
AsyncTask
to solve your threading issues, you should first check outReactiveX/RxAndroid
for a possibly more appropriate programming pattern. A very good resource for getting an overview is Learning RxJava 2 for Android by example.