在Java中,多线程是一种重要的编程概念,它允许多个任务同时执行,从而提高程序的效率和响应速度。这对于需要处理大量数据、执行复杂计算或同时处理多个用户请求的应用程序来说非常有用。
1 多线程基础
在Java中,创建线程主要有两种方式:通过实现`Runnable`接口或继承`Thread`类。`Runnable`接口只有一个`run`方法,它是线程执行的主体。而`Thread`类则是一个具体的线程实现,它实现了`Runnable`接口,并提供了更多的线程控制方法。
一. 实现`Runnable`接口创建线程
public class MyRunnable implements Runnable {
@Override
public void run() {
// 线程执行的代码
}
}
// 创建线程并启动
MyRunnable myRunnable = new MyRunnable();
Thread thread = new Thread(myRunnable);
thread.start();
二. 继承`Thread`类创建线程
public class MyThread extends Thread {
@Override
public void run() {
// 线程执行的代码
}
}
// 创建线程并启动
MyThread myThread = new MyThread();
myThread.start();
1 线程的生命周期
一个线程在其生命周期中会经历不同的状态,如新建、就绪、阻塞、等待、计时等待和终止等。
2 线程同步与通信
在多线程编程中,同步和通信是非常重要的概念。Java提供了`synchronized`关键字以及`wait()`、`notify()`、`notifyAll()`等方法来处理这些问题。
1) `synchronized`关键字
用于确保同一时间只有一个线程可以执行某个代码块或方法,从而避免数据不一致的问题。
2) `wait()`、`notify()`、`notifyAll()`方法
这些方法通常与`synchronized`一起使用,用于实现线程间的通信和协作。
3 实战:生产者消费者问题
生产者消费者问题是一个经典的并发问题,它演示了线程间的同步和通信。
public class SharedBuffer {
private Queue<Integer> items = new LinkedList<>();
private int capacity = 10;
public synchronized void produce(int item) throws InterruptedException {
while (items.size() == capacity) {
wait();
}
items.add(item);
System.out.println("Produced: " + item);
notifyAll();
}
public synchronized int consume() throws InterruptedException {
while (items.isEmpty()) {
wait();
}
int item = items.remove();
System.out.println("Consumed: " + item);
notifyAll();
return item;
}
}
// 生产者线程
class Producer extends Thread {
private SharedBuffer sharedBuffer;
public Producer(SharedBuffer sharedBuffer) {
this.sharedBuffer = sharedBuffer;
}
@Override
public void run() {
for (int i = 0; i < 20; i++) {
try {
sharedBuffer.produce(i);
Thread.sleep(100);
} catch (InterruptedException e) {
e.printStackTrace();
}
}
}
}
// 消费者线程
class Consumer extends Thread {
private SharedBuffer sharedBuffer;
public Consumer(SharedBuffer sharedBuffer) {
this.sharedBuffer = sharedBuffer;
}
@Override
public void run() {
for (int i = 0; i < 20; i++) {
try {
sharedBuffer.consume();
Thread.sleep(100);
} catch (InterruptedException e) {
e.printStackTrace();
}
}
}
}
// 主类
public class ProducerConsumerDemo {
public static void main(String[] args) {
SharedBuffer sharedBuffer = new SharedBuffer();
Producer producer = new Producer(sharedBuffer);
Consumer consumer = new Consumer(sharedBuffer);
producer.start();
consumer.start();
}
}
在这个例子中,生产者线程和消费者线程共享一个缓冲区`SharedBuffer`。生产者线程负责向缓冲区中添加数据,而消费者线程则从缓冲区中取出数据。通过使用`synchronized`关键字和`wait()`、`notifyAll()`方法,生产者线程和消费者线程之间实现了同步和通信,确保了数据的正确性和线程间的协作。