并发编程脑图
2024-02-21 18:00:43 0 举报
AI智能生成
并发
作者其他创作
大纲/内容
ArrayBlockingQueue
LinkedBlockingQueue
PriorityBlockingQueue
缓存系统的设计
定时任务调度
使用场景
DelayQueue
SynchronousQueue
常见4种
在线程池中有比较多的应用,生产者消费者场景
应用场景
基于ReentrantLock保证线程安全
根据Condition实现队列满时的阻塞
工作原理
BlockingQueue API
源码阅读
BlockingQueue
什么是HashMap
高并发下的HashMap
ConcurrentHashMap结构
ConcurrentHashMap
写时复制
获取–修改–写入三个步骤不是原子性
独占锁保证修改数据时只有一个线程能够进行
CopyOnWriteArrayList
并发容器用于读多写少的并发场景。比如白名单,黑名单
场景
读取是完全不用加锁
写入也不会阻塞读取操作
写入的同时进行读取
优点
占用内存
弱一致性
缺点
CopyOnWrite
并发集合
线程几种状态
线程基础
CyclicBarrier
CountDownLatch
Semaphore
并发工具类
单个任务处理时间比较短
需要处理的任务数量很大
什么时候使用线程池?
重用存在的线程,减少线程创建,消亡的开销,提高性能
提高响应速度。当任务到达时,任务可以不需要的等到线程创建就能立即执行。
提高线程的可管理性。
线程池优势
corePoolSize
maximumPoolSize
keepAliveTime
unit
workQueue
threadFactory
AbortPolicy
CallerRunsPolicy
DiscardOldestPolicy
DiscardPolicy
handler
七大参数
线程池流程讲解
FixedThreadPool
SingleThreadExecutor
CachedThreadPool
种类
ThreadPoolExecutor
redis分布式锁
采用定时线程池,假设5秒钟过期。每隔2秒钟去定时续约(续命)一次。看一下redis锁在不在,如果还在则延迟,直到逻辑执行完释放。因为不确定业务逻辑执行多少时间。
看门狗
注册中心Eureka
ScheduledExecutorService
线程池
ThreadLocal
AtomicInteger
AtomicBollean
AtomicLong
基本类型
AtomicIntegerArray
AtomicLongArray
AtomicReferenceArray
数组
AtomicStampedReference
原子更新字段类
引用类型
原子操作
存储器存储空间大小:内存>L3>L2>L1>寄存器;
存储器速度快慢排序:寄存器>L1>L2>L3>内存;
三级缓存结构
如果一个信息项正在被访问,那么在近期它很可能还会被再次访问。
时间局部性
如果一个存储器的位置被引用,那么将来他附近的位置也会被引用。
空间局部性
CPU为何要有高速缓存
Linux与Windows只用到了2个级别:ring0、ring3
CPU从ring3切换ring0创建线程
线程执行JVM程序
线程执行完毕,销毁还得切会ring0
JVM创建线程CPU的工作过程
CPU运行安全等级
CPU缓存结构
用户态
内核态
操作系统内存管理
操作系统底层整认识
JVM运行程序的实体是线程
每个线程创建时JVM都会为其创建一个工作内存(有些地方称为栈空间),存储线程私有的数据
堆
方法区
Java内存模型中规定所有变量都存储在主内存,主内存是共享内存区域
程序计数器
虚拟机栈
本地方法栈
但线程对变量的操作(读取赋值等)必须在工作内存中进行,私有区域
因此不同的线程间无法访问对方的工作内存,线程间的通信(传值)必须通过主内存来完成
什么是JMM
如果存在两个线程同时对一个主内存中的实例对象的变量进行操作
线程安全问题
lock(锁定)
unlock(解锁)
read(读取)
load(载入)
use(使用)
assign(赋值)
store(存储)
write(写入)
八大原子操作
如果要把一个变量从主内存中复制到工作内存中,就需要按顺序地执行read和load操作
如果把变量从工作内存中同步到主内存中,就需要按顺序地执行store和write操作
解释
数据同步
原子性指的是一个操作是不可中断的,即使是在多线程环境下,一个操作一旦开始就不会被其他线程影响
原子性
当一个线程修改了某个共享变量的值,其他线程是否能够马上得知这个修改的值
可见性
有序性是指对于单线程的执行代码,我们总是认为代码的执行是按顺序依次执行的
有序性
synchronized,Lock
保证任一时刻只有一个线程访问该代码块
当一个共享变量被volatile修饰时,它会保证修改的值立即被其他的线程看到,
即修改的值立即更新到主存中,当其他线程需要读取时,它会去主内存中读取新值。
volatile关键字保证可见性
synchronized和Lock也可以保证可见性
volatile
synchronized和Lock
happens-before 原则
不管怎么重排序(编译器和处理器为了提高并行度),(单线程)程序的执行结果不能被改变。
as-if-serial语义
指令重排序
JMM如何解决
原子性,有序性、可见性
JMM(Java内存模型)
保证被volatile修饰的共享变量对所有线程总数可见的
保证特定操作的执行顺序
保证某些变量的内存可见性
内存屏障
instance = new DoubleCheckLock();可以分为以下3步完成(伪代码)
memory = allocate();//1.分配对象内存空间instance(memory);//2.初始化对象instance = memory;//3.设置instance指向刚分配的内存地址,此时instance!=null
由于步骤1和步骤2间可能会重排序,如下:
memory=allocate();//1.分配对象内存空间instance=memory;//3.设置instance指向刚分配的内存地址,此时instance!=null,但是对象还没有初始化完成!instance(memory);//2.初始化对象
单例模式双重检测锁
volatile,private volatile static DoubleCheckLock instance;
禁止重排优化的例子
禁止指令重排序优化
volatile内存语义
通过内部对象Monitor(监视器锁)实现
基本使用
每个同步对象都有一个自己的Monitor(监视器锁)
偏向锁
轻量级锁
重量级锁
锁的膨胀升级过程
锁消除的依据是逃逸分析的数据支持
锁消除
synchronized
同步等待队列、CLH队列
条件等待队列
阻塞等待队列
Exclusive-独占,只有一个线程能执行,如ReentrantLock
Share-共享,多个线程可以同时执行,如Semaphore/CountDownLatch
共享/独占
锁的获取顺序应该符合请求的绝对时间顺序,也就是FIFO。
只要CAS设置同步状态成功,则表示当前线程获取了锁
公平/非公平
可重入
例子
允许中断
AQS具备特性
lock.lock() //加锁
lock.unlock() //解锁
ReentrantLock
ReentrantLock加锁原理
AbstractQueuedSynchronizer
并发编程学习
0 条评论
回复 删除
下一页