1.线程安全问题
1.1原因
多个线程操作同一个数据就会出现线程安全问题
1.2解决思想
多个线程只能有一个线程对数据进行操作
1.3解决方案
方案1:同步代码块
语法:
Synchhronized(锁对象){
要同步的代码
}
上锁与开锁:
当某一个线程进入synchhronized代码块中,其锁对象就会上锁,此时别的线程无法进入,只能在外面等待开锁
当一个线程执行完synchhronized代码块中的代码,此时锁对象就会开锁
注意:
所有的对象可以作为锁对象
要保证多个线程的锁对象是同一个对象
方案2:同步方法
语法:
访问权限修符 synchhonrized 返回值类型 方法名(形参列表){
方法体(要同步的代码)
}
注意:
同步方法的锁对象是调用该方法的对象(同步方法的对象就是this)
方案3:同步静态方法
语法:
访问权限修符 synchhonrized static返回值类型 方法名(形参列表){
方法体(要同步的代码)
}
注意:
同步静态方法的锁对象就是该方法所属的累的类对象
类对象:一个类被jvm加载时会产生一个类对象,该对象包含该类的所有信息,如该类的包名,类名,父类名,实现的接口名,属性数量,属性名,方法数量,方法名等信息
因为一个类只会被加载一次,所以一个类只有一个类对象
2.死锁
2.1目的
了解死锁产生的原因
2.2原因
多个线程互相持有对方所需的锁资源
2.3如何避免
尽量不要再同步中使用同步
3.线程间通讯
3.1方法:
唤醒
锁对象.notify();
作用:随机唤醒一个使用调用该方法的对象作为锁对象的线程
锁对象.notifyAll();
作用:唤醒所有使用调用该方法的对象作为锁对象的线程
休眠
锁对象.wait(); 让当前线程陷入无限期休眠
锁对象.wait(timeout) 让当前线程陷入有限期休眠,参数为休眠时间,单位毫秒
锁对象.wait(timeout,nanos)
作用:让当前线程陷入有限期休眠,休眠时间毫秒+纳秒
参数1休眠时间,单位毫秒
参数2休眠时间,单位纳秒
3.2Wait与sleep的区别
Wait
由object提供的普通方法
只能在同步中使用
休眠期间可以释放持有的锁对象
sleep
由Thread类提供的静态方法
可以在同步在,也可以在同步外使用
休眠期间不会释放持有的锁对象
注意:
- 该方法有object类提供
- 只能在同步代码块或同步方法中使用
- 必须使用该同步代码块或同步方法的锁对象调用
4.生产者与消费者模式
目的:模拟工厂生产与销售的情况
分析: 销售人员类
属性: 工厂
方法: 销售
无限使用工厂对象调用售出方法
生产人员类
属性: 工厂
方法: 生产
无限使用工厂对象调用生产方法
工厂类
属性: 商品数量 最大商品数量
方法:
生产的方法:同步方法
判断商品数量 < 最大商品数量
true:继续生产
商品数量+1 打印谁谁谁生产了一个商品,目前库存xxx个商品
唤醒销售者线程
false
停止当前生产,等待销售 打印库存已满,谁谁谁停止生产
出售的方法:同步方法 判断商品数量大于 > 0
true:可以销售
商品数量-1 打印谁谁谁销售了一个商品,目前库存xxx个商品
唤醒生产者线程
false:无货
停止销售,等待生产 打印无货,谁谁谁停止销售
环境类
创建一个工厂
创建几个生产者
创建几个销售者
启动生产者与销售者