Chapter 13 |
The Thread class
The Thread
class contains the constructors for creating threads for tasks and the methods for controlling threads.
Method | Description |
---|---|
Thread() | Creates an empty thread. |
Thread(task: Runnable) | Creates a thread for a specified task. |
void start() | Starts the thread that causes the run() method to be invoked by the JVM. |
boolean isAlive() | Tests whether the thread is currently running. |
void setPriority(p: int) | Sets priority p (ranging from 1 to 10) for this thread. |
void join() | Waits for this thread to finish. |
static void sleep(millis: long) | Puts a thread to sleep for a specified time in milliseconds. |
static void yield() | Causes a thread to pause temporarily and allow other threads to execute. |
void interrupt() | Interrupts this thread. |
The following program has three tasks and three threads to run them. The tasks are to print integers. When we run this program, three threads will share the CPU and take turns printing numbers on the console.
// The task class for printing numbers from n to m for a given n and m class PrintNum implements Runnable { private int firstNum; private int lastNum; // Construct a task for printing n, n+1, ..., m public PrintNum(int n, int m) { firstNum = n; lastNum = m; } @Override /** Tell the thread how to run */ public void run() { for (int i = firstNum; i <= lastNum; i++) { System.out.print(i + "; "); } } } // Client class public class TestPrintNum{ public static void main(String[] args) { // Create tasks Runnable r1 = new PrintNum(1, 10); Runnable r2 = new PrintNum(20, 30); Runnable r3 = new PrintNum(50, 60); // Create threads Thread t1 = new Thread(r1); Thread t2 = new Thread(r2); Thread t3 = new Thread(r3); // Start threads t1.start(); t2.start(); t3.start(); } }
The sleep(long millis)
method puts a thread to sleep for a specified time in milliseconds to allow other threads to run. For example, suppose we modify the code given above in lines 11–15, as follows:
public void run() { try { for (int i = firstNum; i <= lastNum; i++) { System.out.print(i + "; "); if (i >= 50) Thread.sleep(100); } } catch (InterruptedException e) { throw new RuntimeException(e); } }
Every time a number (>= 50) is printed, the thread of this task is put to sleep for 100 millisecond.
The sleep
method may throw an InterruptedException
, which is a checked exception. The exception may occur when a sleeping thread’s interrupt()
method is called. The interrupt()
method is very rarely invoked on a thread, so InterruptedException
is unlikely to occur. But since Java forces us to catch checked exceptions, we have to put the thread into a try-catch
block. If a sleep
method is invoked in a loop, we should wrap the loop into a try-catch
block, as shown in the example. If the loop is outside the try-catch
block, the thread may continue its work even though it is being interrupted.
We can use the join()
method to force one thread to wait for another thread to finish. For
example, suppose we modify the code given above in lines 30-32.
// Start threads t1.start(); t1.join(); t2.start(); t3.start();
Threads t2
and t3
will continue their work after thread t1
has finished its work.
Java assigns every thread a priority. By default, a thread inherits the priority of the thread that spawned it. We can increase or decrease the priority of any thread by using the setPriority
method, and we can get the thread’s priority by using the getPriority
method. Priorities are numbers ranging from 1 to 10. The Thread
class has the int
constants MIN_PRIORITY
, NORM_PRIORITY
, and MAX_PRIORITY
, representing 1, 5, and 10, respectively. The priority of the main thread is Thread.NORM_PRIORITY
. The JVM always picks the currently runnable thread with the highest priority. A lower priority thread can run only when no higher-priority threads are running. If all runnable threads have equal priorities, each one is assigned an equal portion of the CPU time in a circular queue. This is called round-robin scheduling. For example, suppose we insert the following code in line 31:
t2.setPriority(Thread.MAX_PRIORITY);
The thread for the r2
task will be finished first.
Chapter 13 |