线程同步对应的方案总结:
1 适用范围
可见性:volatile 适用范围:比如状态值,简单的 写,读,synchronized 适应所有可见性的情况
原子性:atomic包,cas算法,synchronized,lock 适用范围:比如一些复杂的++ -- 对象赋值等操作
有序性,都能保证(volatile,atomic,synchronized,lock等等)
2 使用流程:
volatile>cas>atomicStampreference>synchronized,lock
cas有aba问题,大于两个以上的线程建议用atomicStampreference
synchronized 底层通过虚拟机保证只有一个线程执行保证了原子性,通过内存屏障(就是进入屏障的,都要写入主内存,都要必须不重排)
来保证有序性,可见性,这点和volatile是一样的(内部流程,先偏向锁,就是同一个线程访问无需枷锁,然后cas,然后重型锁,但是呢,他是超时后才转换,
转换不够灵活,我们还是自己选择的好)
3 线程池相关的
单线程池和有限线程池队列是无限制,会导致oom
cached 和scheduled 线程池线程量无限制,会导致oom,
排队队列可以选 有限,无限,双端等队列,拒绝策略有 报错,丢弃,替换最后一个队列的任务等等
最好给一个公用的异常处理策略
1 给每个线程添加异常处理类
threadFactory(线程工厂)。这是用来创建线程的工厂,这里可以创建thread的时候添加异常处理
返回一个setUncaughtExceptinHandler的thread类
2 给所有线程添加异常处理类
4 wait,notify,join
这里主要记录下一些使用范例:
1 获得锁后,仍然需要重新检查下条件
synchronized(对象){
while(条件不满足){
对象.wait();
}
对应的处理逻辑
}
另外尽量用notifyall(notify是给一个wait线程走,notifyall是所有wait的退出后,从新while判断条件后走)
2 一定要明确锁加在了哪个对象上,不然默认加在当前对象,容易导致同步操作无效或
IllegalMonitorStateException: object not locked by thread before notify
这个在异步加载中用到过,就是放到了子线程来初始化一部分耗时操作,此期间不能访问(wait),当时用的是默认的 notify
导致一系列问题,所以要明确notify,wait的对象,要用object.wait,object.notifyall才行