Android thread Management (iii) Internal principles of the--thread class, hibernation and wake-up

Source: Internet
Author: User

Thread communication, Activitythread, and thread classes are key to understanding Android threading management.

threads, as the basic unit of CPU scheduling resources, have a very important and fundamental role in the operating system for embedded devices such as Android. This section is mainly from the following three aspects of analysis:

    1. "Android thread Management (i)--thread communication"
    2. "Android Threading Management (ii)--activitythread"
    3. Android Threading Management (iii) Internal principles, sleep and wake of the--thread class
Third, the internal principle of the thread class, sleep and wake 3.1 The internal principle of the thread class

Thread is the basic unit of CPU resource scheduling, which belongs to the abstract category, and Java completes thread management through the thread class. The essence of the thread class is actually "executable code", which implements the Runnable interface, and the only method of the Runnable interface is run ().

Runnable {...}
Runnable {    /**     * Starts executing the active part of the class ' Code. This method was     * Called when a thread was started that had been created with a class which     * implements {void R Un ();} 

As you can see from the note, the start () method that calls the thread is called indirectly by the Run () method of the Runnable interface.

void Start () {    checknotstarted ();    true;    Vmthread.create (this, stackSize);} 

The start () method in Vmthread.create (this, stackSize) is the place where the CPU thread is actually created, in other words, only the thread after the call to start () actually creates the CPU thread, The newly created thread is running the run () method of the Runnable interface.

3.2 Thread hibernation and wake-up

Thread communication, synchronization, and collaboration are common problems in multithreaded programming. Thread collaboration is usually implemented with thread hibernation and wakeup, and the thread's hibernation is implemented by waiting for an object's lock (Wait () method), which is awakened when other threads invoke the object's notify () method. This object implements data passing between threads, which is the object through which more than one thread is collaborating.

The classic example of threading collaboration is the "producer-consumer model" in Java design patterns, where producers continue to write data to buffers, and consumers take data out of buffers to consume. In the implementation, the producer and consumer inherit thread respectively, the buffer is modeled by the priority queue Priorityqueue. The producer puts the data in the buffer as long as the buffer has space left, and the consumer pulls the data out of the buffer as long as there is data in the buffer, so this involves collaboration between the generator thread and the consumer thread. Below is a brief description of the code.

Import Java.util.PriorityQueue;PublicClasstestwait {Privateint size =5;Private priorityqueue<integer> queue =New priorityqueue<integer> (size);PublicStaticvoid Main (string[] args) {testwait test =New Testwait (); Producer Producer = Test.New Producer (); Consumer Consumer = Test.New Consumer (); Producer.start (); Consumer.start (); }ClassConsumerExtendsThread {@OverridePublicvoid Run () {while (True) {Synchronized (queue) {while (queue.size () = =0) {try {System.out.println ("Queue empty, wait for data"); Queue.wait (); }catch (Interruptedexception e) {e.printstacktrace (); Queue.notify ();}} Queue.poll ();Each removal of the first element of the team queue.notify (); System.out.println ("Take an element from the queue, queue remaining" + queue.size () + "elements"); }}}} class producer extends Span class= "title" >thread { @Override public  void Run () {while (true) {synchronized (queue) { span class= "keyword" >while (queue.size () = = size) {try {System.out.println (  "queue full, waiting for free space"); Queue.wait (); } catch (interruptedexception e) {e.printstacktrace (); Queue.notify ();}} queue.offer (1); //inserts one element at a time queue.notify (); System.out.println ( "Inserts an element into the queue, the remaining space of the queue:" + (Size-queue.size ()));}} } }} 

This code is used in many places where the producer-consumer model is described, where the producer thread starts first, the Synchronized keyword enables it to get the lock on the queue, and the other threads are waiting. The initial queue is empty, writes data to the buffer queue through an offer, and the Notify () method wakes the thread waiting for the queue in the buffer (where the consumer thread is), but the thread does not immediately get the queue lock. Only when the producer thread continues to write data to the queue until queue.size () = = size, when the buffer queue is filled, the producer thread calls the Wait () method into the waiting state. At this point, the consumer thread wakes up and obtains the lock of the queue, consumes the data in the buffer through the poll () method, and, similarly, calls the Notify () method to cause the producer thread to wake up, but it does not immediately get the queue lock. Only when the consumer thread continues to consume data until queue.size () = = 0, the consumer thread calls the Wait () method into the waiting state, the producer thread re-obtains the queue lock, loops over the process, and completes the collaboration between the producer thread and the consumer thread.

There are many ways to use thread collaboration in Android Systemserver, such as Windowmanagerservice's main () through Runwithscissors () The blockingrunnable initiated collaboration with the Systemserver thread. Windowmanagerservice Source address can be consulted: Https://github.com/android/platform_frameworks_base/blob/master/services/core/java /com/android/server/wm/windowmanagerservice.java

3.3 Thread interrupts

In Java, the "break" thread is implemented through the interrupt () method, because interrupt () does not break the running thread, but only sends an interrupt request to the thread, depending on the state of the thread, as described in the documentation:

Posts an interrupt request toThis Thread. The behavior depends on the state of this thread:threads blocked in one of the  Object' s Wait () methods or one of T Hread ' s join () or sleep () methods is woken up, their interrupt status'll be cleared, and they receive an interr Uptedexception. Threads blocked in an I/O operation of an java.nio.channels.InterruptibleChannel would have their interrupt status  Set and receive an java.nio.channels.ClosedByInterruptException. Also, the channel would be closed. Threads blocked in a java.nio.channels.Selector would have their interrupt status set and return immediately. T Hey Don' t receive a exception           in the case.

Translated by:

    • If the thread is in a blocked state, that is, the thread is blocked by object.wait (), Thread.Join (), or Thread.Sleep (), the interrupt () method is called, the interruptedexception exception is received, and the interrupt state is cleared To end the blocking state;
    • If the thread is i/ O operation (Java.nio.channels.InterruptibleChannel) is blocked, then the thread will receive an java.nio.channels.ClosedByInterruptException exception, the channel is closed, the blocking state is ended;
    • If the thread is blocked in Java.nio.channels.Selector, the interrupt state is set and returned, and no exception is thrown.
void Interrupt () {    //Interrupt this thread before running the actions so, other    //threads that observe t He interrupt as a result of an action//would see that this thread was in the    interrupted state.    For (0; i--) {interruptactions.  Get (i). Run (); } }}
3.4 Join () and sleep () methods

The join () method can also be understood as a way of collaborating between threads, and when two threads need to execute sequentially, the join () method that invokes the first thread can block the thread, which is still implemented by the wait () method.

/** * Blocks the current Thread (<code> Thread.CurrentThread () </code>) until * The receiver finishes its execution and dies.         * *  @throws interruptedexception if <code>interrupt () </code> was called for * The receiver while it is in the <code>join () </code> call *  @see Object#notifyall *  @see java.lang.ThreadDeath */public final span class= "keyword" >void join () throws interruptedexception {vmthread t = vmthread; if (t = = null) {return;} synchronized (t) {while (isAlive ()) {t.wait ();}}}    

In addition, there is a join () method with a time parameter, which exits the blocking state after a specified time has been exceeded. Similarly, it is implemented by the wait () method with time parameters.

void Join (throws interruptedexception{}void Join (throws interruptedexception {}  

Sleep () is identical to wait () in that they all wait for the thread to be blocked, except that sleep () waits for the time, and wait () waits for the object's lock.

void Sleep (throws interruptedexception {    0);} 
void Sleep (throws interruptedexception {vmthread.sleep (Millis, Nanos);}
3.5 Countdownlatch

The Countdownlatch is located in Java.util.concurrent.CountDownLatch, which implements a count-down latch that triggers a specific event when the count is reduced to 0 o'clock. Some of the main threads need to wait until the sub-threading application is useful, as illustrated by a snippet from Google's zxing Open Source Library:

FinalClassDecodethreadExtendsthread {... private final countdownlatch handlerinitlatch; Decodethread (captureactivity activity, collection<barcodeformat> decodeformats, map<decodehinttype,?> Basehints, String CharacterSet, Resultpointcallback resultpointcallback) {this.activity = Activity Handlerinitlatch = new countdownlatch (1); Handler GetHandler () {try {handlerinitlatch.await ();} catch (interruptedexception IE) {//continue?} return handler;}  @Override public void run () {Looper.prepare () ; Handler = new decodehandler (activity, hints); Handlerinitlatch.countdown (); Looper.loop (); }}

In the above example, the Countdownlatch object is initialized in the Decodethread constructor, and the initialization parameter 1 is passed in. Second, the countdown () method of the Countdownlatch object is called in the Run () method, which ensures that handler is not NULL when an external instance obtains handler through the GetHandler () method.

Android thread Management (iii) Internal principles of the--thread class, hibernation and wake-up

Related Article

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.