Run the code task instance in the Android thread pool
- 2020-06-01 11:01:06
- OfStack
This section shows how to perform tasks in a thread pool. The process is to add a task to the work queue of the thread pool, and when a thread becomes available (after executing other tasks, idle, or not yet executing a task),ThreadPoolExecutor will fetch the task from the queue and run it in the thread.
This lesson also shows you how to stop a running task.
Performs tasks on threads in the thread pool
The Runnable object is passed in ThreadPoolExecutor.execute () to start the task. This method adds tasks to the thread pool work queue. When a thread is free, the manager pulls out the task that has been waiting the longest and runs it on the thread.
public class PhotoManager {
public void handleState(PhotoTask photoTask, int state) {
switch (state) {
// The task finished downloading the image
case DOWNLOAD_COMPLETE:
// Decodes the image
mDecodeThreadPool.execute(
photoTask.getPhotoDecodeRunnable());
...
}
...
}
...
}
When ThreadPoolExecutor starts Runnable, the run() method is automatically called.
Interrupts running code
To stop a task, you need to interrupt the progress of the task. You need to save the handle of the current thread while creating the task.
Such as:
class PhotoDecodeRunnable implements Runnable {
// Defines the code to run for this task
public void run() {
/*
* Stores the current Thread in the
* object that contains PhotoDecodeRunnable
*/
mPhotoTask.setImageDecodeThread(Thread.currentThread());
...
}
...
}
To interrupt the thread, call Thread.interrupt (). Tip: thread objects are system-controlled and can be edited outside of your app process. For this reason, you need to put an access lock in a synchronized block before breaking it:
public class PhotoManager {
public static void cancelAll() {
/*
* Creates an array of Runnables that's the same size as the
* thread pool work queue
*/
Runnable[] runnableArray = new Runnable[mDecodeWorkQueue.size()];
// Populates the array with the Runnables in the queue
mDecodeWorkQueue.toArray(runnableArray);
// Stores the array length in order to iterate over the array
int len = runnableArray.length;
/*
* Iterates over the array of Runnables and interrupts each one's Thread.
*/
synchronized (sInstance) {
// Iterates over the array of tasks
for (int runnableIndex = 0; runnableIndex < len; runnableIndex++) {
// Gets the current thread
Thread thread = runnableArray[taskArrayIndex].mThread;
// if the Thread exists, post an interrupt to it
if (null != thread) {
thread.interrupt();
}
}
}
}
...
}
In most cases, Thread.interrupt () stops the thread immediately. However, it only stops the waiting thread, but does not interrupt the cpu or network-intensive tasks. To prevent the system from slowing down, you should test the request waiting for an interrupt before attempting the operation.
/*
* Before continuing, checks to see that the Thread hasn't
* been interrupted
*/
if (Thread.interrupted()) {
return;
}
...
// Decodes a byte array into a Bitmap (CPU-intensive)
BitmapFactory.decodeByteArray(
imageBuffer, 0, imageBuffer.length, bitmapOptions);
...