一、内存可见性问题:多个线程操作共享数据时,会将共享数据放到各自缓存中,
解决:volatile关键字 使共享数据在内存可见
二、但是volatile关键字不能保证”原子性”,也没有“互斥性”
jdk1.5之后提供了常用的原子变量:1volatile保证内存可见性 2、cas算法
三、新增并发安全类
currentHashMap:线程安全,效率较currenthashtable高
copyonwriteArrayList:线程安全,适用场景 迭代多、增删少的场景,原因是每次增删都会重新复制一份新的
四、countDownLatch :闭锁,等待所有线程准备完毕一起执行
public class testCountDownLatch {
public static void main(String[] args) {
//创建一个CountDownLatch对象,指定等待的线程数为5
CountDownLatch cdl = new CountDownLatch(5);
work w = new work(cdl);
Thread th =new Thread(w);
for(int i=0 ;i<5;i++){
th.start();
}
try {
//主线程等待
cdl.await();
} catch (InterruptedException e) {
e.printStackTrace();
}
System.out.println("主线程开始执行");
}
}
class work implements Runnable{
CountDownLatch cdl = null;
public work(CountDownLatch cdl){
this.cdl = cdl;
}
@Override
public void run(){
//多线程操作cdl,加锁保证线程安全
synchronized (this){
try {
for(int i=0;i<100;i++){
System.out.println(i);
}
} finally {
//每次执行线程,这个数字减一,到0时主线程往下执行
cdl.countDown();
}
}
}
}
五、futureTask 也可用于闭锁 结合callable接口使用,具有返回值,可以得到线程执行结束通知
六、 在生产者消费模型中,两个以上的生产者和消费者会存在虚假唤醒的情况,这个时候应当把wait()方法写到while循环中,在每次唤醒时再判断一次,防止虚假唤醒
七、lock类
1.普通锁
//在需要加锁的位置创建锁对象
Lock lock = new ReentrantLock();
//创建一个锁的操作对象Condition
Condition condition = lock.newCondition();
//线程等待,类似thread.wait()
condition.await();
//随机唤醒一个线程 类似notify
condition.signal();
//唤醒全部线程 类似notifyAll
condition.signalAll();
2.有特点的锁:读写锁
//读写锁
ReadWriteLock readWriteLock = new ReentrantReadWriteLock();
//读锁可以多个线程同时进行
readWriteLock.readLock();
//写锁只能有一个线程独占
readWriteLock.writeLock();
八、线程八锁关键:
1.非静态方法持有的锁为this,即当前对象
2.静态方法持有的锁为 Class对象
3.同一时间一把锁只能被一个线程持有
注意点;静态方法和非静态方法持有的锁是不同的
九、线程池
本文深入探讨Java并发编程的关键概念,包括内存可见性问题及volatile关键字的作用,原子变量的使用,以及concurrentHashMap和copyonwriteArrayList等并发安全类的特点。此外,还介绍了闭锁机制如CountDownLatch和futureTask的用法,线程间通信的优化技巧,Lock类的高级应用,以及线程池的设计原理。
1125

被折叠的 条评论
为什么被折叠?



