在Java中,线程管理是一个关键的议题,因为线程是程序中并发执行的最小单元。Java提供了多种方式来创建和管理线程,以下是一些主要的概念和方法:
1. 创建线程
线程可以通过继承Thread
类或实现Runnable
接口来创建。
继承Thread
类:
class MyThread extends Thread {
public void run() {
// 线程执行的代码
}
}
// 创建和启动线程
MyThread t = new MyThread();
t.start();
实现Runnable
接口:
class MyRunnable implements Runnable {
public void run() {
// 线程执行的代码
}
}
// 创建和启动线程
Thread t = new Thread(new MyRunnable());
t.start();
2. 线程的生命周期
线程的生命周期包括新建、可运行、运行、阻塞、死亡等状态。
- 新建状态:线程对象已被创建,但还没有调用
start()
方法。 - 可运行状态:线程已经调用了
start()
方法,等待CPU时间片。 - 运行状态:线程正在执行
run()
方法中的代码。 - 阻塞状态:线程因为某些原因(如等待I/O操作、等待同步锁)暂时停止运行。
- 死亡状态:线程的
run()
方法执行完毕,或者因为异常退出了run()
方法。
3. 线程的同步
线程同步是确保多个线程在访问共享资源时保持一致性的一种机制。
使用synchronized
关键字:
public class Counter {
private int count = 0;
public synchronized void increment() {
count++;
}
public synchronized int getCount() {
return count;
}
}
使用ReentrantLock
:
import java.util.concurrent.locks.ReentrantLock;
public class Counter {
private final ReentrantLock lock = new ReentrantLock();
private int count = 0;
public void increment() {
lock.lock();
try {
count++;
} finally {
lock.unlock();
}
}
public int getCount() {
lock.lock();
try {
return count;
} finally {
lock.unlock();
}
}
}
4. 线程池
线程池用于管理和优化线程的创建和销毁,提高资源利用率。
使用ExecutorService
:
import java.util.concurrent.ExecutorService;
import java.util.concurrent.Executors;
// 创建线程池
ExecutorService executor = Executors.newFixedThreadPool(10);
// 提交任务给线程池
executor.execute(new MyRunnable());
// 关闭线程池
executor.shutdown();
5. 线程通信
线程通信是指线程之间进行数据交换和协调的方法。
使用wait()
和notify()
:
public class BoundedBuffer {
private final Object[] items = new Object[10];
private int putPtr, takePtr, count;
public synchronized void put(Object x) throws InterruptedException {
while (count == items.length) {
wait();
}
items[putPtr] = x;
if (++putPtr == items.length) putPtr = 0;
++count;
notify();
}
public synchronized Object take() throws InterruptedException {
while (count == 0) {
wait();
}
Object x = items[takePtr];
if (++takePtr == items.length) takePtr = 0;
--count;
notify();
return x;
}
}
6. 线程的高级特性
Java还提供了一些高级特性,如Callable
、Future
、Phaser
、Fork/Join
等,用于更复杂的并发编程场景。
使用Callable
和Future
:
import java.util.concurrent.Callable;
import java.util.concurrent.FutureTask;
Callable<Integer> task = new Callable<Integer>() {
public Integer call() {
return 123;
}
};
FutureTask<Integer> future = new FutureTask<>(task);
// 创建和启动线程
Thread t = new Thread(future);
t.start();
// 获取任务结果
Integer result = future.get();
总结
Java提供了丰富的API和工具来管理线程,从创建和同步到线程池和线程通信。理解和正确使用这些工具对于编写高效、可靠的并发程序至关重要。