多线程详解
多线程详解
- 线程简介
- 线程实现(重点)
- 线程状态
- 线程同步(重点)
- 线程通信问题
- 高级主题
线程简介
Process与Thread

-
程序是指令和和数据的集合,其本身没有任何运行的含义,是一个静态的概念。
-
而进程则是执行程序的一次执行过程,他是一个动态的概念。是系统资源分配的单位。
-
通常在一个进程中可以包含若干个线程,当然一个进程中至少有一个线程,不然没有存在的意义。线程是CPU调度和执行的单位。
注意:很多多线程是模拟出来的,真正的线程是指有多个CPU,即多核,如服务器。如果是模拟出来的多线程,即在一个CPU的情况下,在同一个时间点,CPU只能执行一个代码,因为切换的很快,所以就有同时执行的错觉。
线程实现
创建线程
-
继承Thread类,重写run方法
package com.yuan.threadlesson; //创建线程方式一:继承Thread类, 重写run()方法,调用start开启线程 public class TestThread1 extends Thread{ @Override public void run() { for (int i=0;i<200;i++){ System.out.println("nihao"+i); } } public static void main(String[] args) { TestThread1 testThread1 = new TestThread1(); testThread1.start(); for (int i = 0; i < 200; i++) { System.out.println("niyehao"+i); } } }
-
实现Runnable接口。
package com.yuan.threadlesson; public class TestThread2 implements Runnable{ @Override public void run() { for (int i = 0; i < 20; i++) { System.out.println("我在看代码"+i); } } public static void main(String[] args) { TestThread2 testThread2 = new TestThread2(); new Thread(testThread2).start(); for (int i = 0; i < 20; i++) { System.out.println("nihao"+i); } } }
静态代理
线程状态
-
线程停止
-
线程休眠
-
Thread.sleep()
-
-
线程礼让
-
Thread.yield()
-
-
强制执行
-
Thread.join()
-
-
线程优先级
-
Thread.setPriority()
-
-
线程守护
-
Thread.setDaemon(true);//默认是false表示的 是用户线程,正常的线程都是用户线程
-
线程同步
-
线程同步含义:多个线程操作同一个资源
-
对比:并发,同一个对象被多个线程同时操纵
-
形成条件:队列和锁
-
线程同步方式:同步锁的对象应该是变化的量
-
同步方法,synchronized 修饰方法
//如下所示 private synchronized void buy() {} //同步方法,synchronized默认,锁的是this
-
同步块
synchronized (obj){//obj 对象 //执行代码块 }
-
锁
-
死锁:多个线程(两个及以上)互相抱着对方需要的资源,然后形成僵持。
-
lock(锁),从JDK5.0开始,java提供了更强大的线程同步机制---通过显式定义同步锁对对象来实现同步。同步锁使用Lock对象充当
-
//定义lock锁 ReentrantLock--可重复锁 ReentrantLock lock = new ReentrantLock();
-
线程协作
-
线程通信
- 生产者消费者模式(问题)
- 对于生产者,没用生产产品之前,要通知消费者等待,而生产了产品之后,又需要马上通知消费者消费
- 对于消费者,在消费者后,要通知生产者已经结束消费,需要生产新的产品以供消费。
- 在生产者消费者问题中,仅有synchronized是不够的
- synchronized可阻止并发更新同一个共享资源,实现了同步
- synchronized不能用来实现不同线程之间的消息传递(通信)
package com.yuan.threadlesson; //生产者消费者问题1 public class TestPc { public static void main(String[] args) { SynContainer container = new SynContainer(); new Producer(container).start(); new Consumer(container).start(); } } //生产者 class Producer extends Thread{ SynContainer container; public Producer(SynContainer container){ this.container = container; } //生产 @Override public void run() { for (int i = 0; i < 100; i++) { System.out.println("生产了"+i+"只鸡"); container.push(new Chicken(i)); } } } //消费者 class Consumer extends Thread{ SynContainer container; public Consumer(SynContainer container){ this.container = container; } //消费 @Override public void run() { for (int i = 0; i < 100 ; i++) { System.out.println("消费了--->"+container.pop().id+"只鸡"); container.pop(); } } } //生产者生产的产品 class Chicken{ int id; public Chicken(int id) { this.id = id; } } //缓存区 class SynContainer extends Thread{ //存放产品的仓库容量 Chicken[] chickens = new Chicken[10] ; //产品数量 int count=0; //生产者存放产品 public synchronized void push(Chicken chicken){ //如果生产达到消费需求,通知消费者消费 while (count==chickens.length){ try { wait(100); } catch (InterruptedException e) { e.printStackTrace(); } } //如果没有满,我们需要继续生产 chickens[count] = chicken; count++; this.notifyAll(); } //消费者消费产品 public synchronized Chicken pop(){ while (count==0){ //等待生产者生产,消费者等待 try { wait(100); } catch (InterruptedException e) { e.printStackTrace(); } } count--; Chicken chicken = chickens[count]; this.notifyAll(); return chicken; } }
- 生产者消费者模式(问题)
使用线程池
-
JDK5.0起提供了线程池相关API:ExectutorService和EXecutors
-
package com.yuan.threadlesson; import java.util.concurrent.Executor; import java.util.concurrent.ExecutorService; import java.util.concurrent.Executors; public class TestPool { public static void main(String[] args) { //1.创建服务,创建线程池 ExecutorService service = Executors.newFixedThreadPool(10); //执行 service.execute(new myThread()); service.execute(new myThread()); service.execute(new myThread()); service.execute(new myThread()); //关闭连接 service.shutdown(); } } class myThread implements Runnable{ @Override public void run() { for (int i = 0; i < 4; i++) { System.out.println(Thread.currentThread().getName()); } } }
【推荐】编程新体验,更懂你的AI,立即体验豆包MarsCode编程助手
【推荐】凌霞软件回馈社区,博客园 & 1Panel & Halo 联合会员上线
【推荐】抖音旗下AI助手豆包,你的智能百科全书,全免费不限次数
【推荐】博客园社区专享云产品让利特惠,阿里云新客6.5折上折
【推荐】轻量又高性能的 SSH 工具 IShell:AI 加持,快人一步
· 一个费力不讨好的项目,让我损失了近一半的绩效!
· 清华大学推出第四讲使用 DeepSeek + DeepResearch 让科研像聊天一样简单!
· 实操Deepseek接入个人知识库
· CSnakes vs Python.NET:高效嵌入与灵活互通的跨语言方案对比
· Plotly.NET 一个为 .NET 打造的强大开源交互式图表库