线程-相关知识点

业精于勤而荒于嬉,行成于思而毁于随。

java内存模型

java内存模型(java memory model)是一种规范,是解决多线程在用共享内存时,因为3级缓存,编译器重排,cpu乱序执行,导致的线程安全问题。
3种问题:原子性,可见性,有序性

关键字volatile

保证可见性,有序性
在实现双重检测单例时,就是因为利用了有序性,保证创建对象时按照分配内存->内存中创建对象-> 变量指向内存的执行顺序。
不能保证原子性,导致一些依赖原值的修改操作,在多线程中会出现问题。
可以用AtomicInteger->longAdder(分段cas并发时性能好)来实现线程安全。(基于CAS)
写操作前插入写写、写操作后添加写读、读操作前添加读读、读操作后添加读写内存屏障,保证可见性和有序性。

实现线程安全思路
  • 锁(s锁,AQS锁
  • cas(AtomicInteger
  • 一个线程一套(ThreadLocal
S锁

jdk1.5实现,是个笨锁,操作有用户态内核的上下文切换。
jdk1.6升级了,根据竞争程度一级一级升级。这里也涉及到了自旋锁,因为自旋锁在竞争比较激烈比较费cpu,所以最后转为笨锁,一了百了。


image.png
CAS算法

内存值,旧值,新值
线程旧值新值运算完之后,回写内存值时,对比内存值旧值是否相等。
ABA问题可以加版本号处理。
争抢比较多比较费cpu,但是比起s锁没有上下文切换开销。

AQS抽象同步队列

state为0说明没有正在运行的线程,可以直接运行,运行会把state改为1,这时候如果还是这个线程重入加锁,会再进行累加。
双向链表(CHL),有正在运行的线程,又不是自己,r锁默认是非公平锁,会先加到尾插到链表里。
r锁默认是非公平锁,可以创建的时候指定,非公平锁时新加锁的线程会先cas2次去争抢锁,抢到就继续执行,否则park放到链表尾部。公平锁模式,会直接放到park链表尾部。非公平锁具有更高的吞度量,因为新加入线程可能直接执行,没有暂停,放入队列,再唤醒的开销。

Locksupport.park

  • 响应中断,但不抛出异常。
  • 底层permit布尔值,控制挂起执行。

封装的一些类:

  1. ReentrantLock
    比起s锁,公平锁,可中断,有状态。
    代码块,需要手动释放。
    lock.Condition实现了s锁的wait nofity机制。
    对应await,signal方法。
  2. ReentrantReadWriteLock 读写锁。
  3. Semaphore 信号量,控制线程的数量。
    acquire()数量加一,满了阻塞。
    release()数量减一。
  4. CountDownLatch 倒计时 实现线程同时运行。
    await()阻塞,等待数减到0。
    countdown()数量减一。
  5. CyclicBarrier 循环屏障(比起countdownLatch可以复用reset)
    await()阻塞,当所有数量线程都走到此步,继续执行。
ThreadLocal

https://www.jianshu.com/p/a20af7b7d113

image.png

最后编辑于
©著作权归作者所有,转载或内容合作请联系作者
平台声明:文章内容(如有图片或视频亦包括在内)由作者上传并发布,文章内容仅代表作者本人观点,简书系信息发布平台,仅提供信息存储服务。

推荐阅读更多精彩内容

  • 线程基本知识 什么是线程安全性?当多个线程访问某个类时,这个类始终都能表现出正确的行为,那么可以认为这个类是线程安...
    Cheava阅读 1,039评论 0 1
  • 这次说说多线程只是扩展,主要讲解一些应用,应用带一些原理讲解,同时希望各位老铁有所收获,这些内容跟前面的线程和并发...
    IT人故事会阅读 455评论 0 1
  • 一、知识结构分析 多线程之间的关系 pthread是POSIX线程的API NSThread是Cocoa对pthr...
    huoshe2019阅读 503评论 0 4
  • 线程相关的,现在基本上都是核心,这个必须要会。 正文 有一个大的逻辑前提,就是计算机其实分为用户层和系统层的,操作...
    头秃到底阅读 199评论 0 0
  • 多线程技术概述 线程与进程 进程是指一个内存中运行的应用程序,每个进程都有一个独立的内存空间 线程 是进程中的一个...
    绮筠阅读 112评论 0 0