![](https://img-blog.csdnimg.cn/20201014180756780.png?x-oss-process=image/resize,m_fixed,h_224,w_224)
并发编程
文章平均质量分 83
并发编程相关技术文章
每天都要进步一点点
工作日常技术学习、积累、总结
展开
-
锁擦除和锁粗化
锁擦除是指虚拟机即时编译器(JIT)在运行时,对一些代码上要求同步,但是被检测到不可能存在共享数据竞争的锁进行擦除。锁擦除的主要判定依据来源于逃逸分析的数据支持,如果判断在一段代码中,堆上的所有数据都不会逃逸出去从而被其他线程访问到,那就可以把它们当做栈上数据对待,认为它们是线程私有的,同步加锁自然就无须进行。原则上,我们在编写代码的时候,总是推荐将同步块的作用范围限制得尽量小,只在共享数据的实际作用域中才进行同步,这样是为了使得需要同步的操作数量尽可能变小,如果存在锁竞争,那等待锁的线程也能尽快拿到锁。.原创 2022-08-29 10:23:33 · 329 阅读 · 0 评论 -
synchronized锁升级之重量级锁
当有大量的线程都在竞争同一把锁的时候,这个时候加的锁,就是重量级锁。//锁对象的原始对象头//抢占当前锁的线程数量_waiters = 0, //调用wait方法后等待的线程数量//记录锁重入次数//指向持有ObjectMonitor的线程//处于wait状态的线程队列,等待被唤醒//等待锁的线程队列}......原创 2022-08-26 09:30:08 · 712 阅读 · 0 评论 -
synchronized锁升级之轻量级锁
轻量级锁是JDK 6之中加入的新型锁机制,它名字中的“轻量级”是相对于使用monitor的传统锁而言的。轻量级锁指的是存在多线程竞争,但是任意时刻最多只允许一个线程竞争获得锁,即不存在锁竞争太过激烈的情况,轻量级锁情况下,线程不会发生阻塞。原创 2022-08-24 09:46:15 · 1561 阅读 · 1 评论 -
synchronized锁升级之偏向锁
HotSpot作者经过研究实践发现,在大多数情况下,锁不仅不存在多线程竞争,而且总是由同一线程多次获得,为了让线程获得锁的代价更低,引进了偏向锁。偏向锁的“偏”,它的意思是锁会偏向于第一个获得它的线程,会在对象头(Mark Word中)存储锁偏向的线程ID,以后该线程进入和退出同步块时只需要检查是否为偏向锁、锁标志位以及ThreadID即可。...原创 2022-08-19 09:57:45 · 1261 阅读 · 0 评论 -
synchronized锁升级之无锁
synchronized同步锁相关信息保存到锁对象的对象头里面的Mark Word中,锁升级功能主要是依赖Mark Word中锁标志位和是否偏向锁标志位来实现的。为了优化synchronized锁的效率,在JDK6中,HotSpot虛拟机开发团队提出了锁升级的概念,包括偏向锁、轻量级锁、重量级锁等,锁升级指的就是“从上图我们可以看到,无锁对应的锁标志位是“01”,是否偏向锁标志是“0”。无锁 --> 偏向锁 --> 轻量级锁 --> 重量级锁。......原创 2022-08-15 13:17:01 · 513 阅读 · 0 评论 -
synchronized的工作原理
synchronized是一个同步关键字,在某些多线程场景下,如果不进行同步会导致共享数据不安全,而synchronized关键字就可以用于代码同步。修饰普通同步方法锁的对象是当前实例对象;修饰静态同步方法锁的对象是当前的类的Class字节码对象;修饰同步代码块锁的对象是synchronized后面括号里配置的对象,可以是某个对象,也可以是某个类的.class对象;......原创 2022-08-12 10:11:06 · 772 阅读 · 0 评论 -
对象内存布局
在HotSpot虚拟机中,对象在内存中存储的布局可以分为三块区域:对象头(Header)、实例数据(Instance Data)和对齐填充(Padding)。原创 2022-08-11 11:30:32 · 624 阅读 · 0 评论 -
Compare And Swap(CAS)总结
目录一、什么是CAS二、CAS的原理分析三、JDK中对CAS的支持 — Unsafe类四、自旋锁五、CAS的缺点六、CAS的使用场景CAS的全称是Compare-And-Swap,它是一条CPU的原子指令,不会有线程安全问题,CAS是实现并发算法时常用到的一种技术。CAS是解决多线程并行情况下使用锁造成性能损耗的一种机制,CAS操作包含三个操作数——内存位置(V)、预期值(A)和新值(B)。如果内存位置的值与预期值相匹配,那么处理器会自动将该位置值更新为新值。否则,处理器不做任何操作,多个线程同时执行CAS原创 2022-07-13 17:29:09 · 3148 阅读 · 1 评论 -
线程的中断标志位为true,是不是线程就立即停止?
看下面的代码:输出结果: 通过运行结果,可以总结出以下几点:原创 2022-06-24 13:51:06 · 465 阅读 · 0 评论 -
如何停止中断运行中的线程?
线程中断就是处于运行状态的线程被强制打断。线程中断总体来说有三种方法:正常退出、stop暴力停止、interrupt()中断停止。其中使用stop()方法是不安全的,可能导致数据不同步或者资源无法回收,目前stop()方法已经被标注为作废方法,我们通常使用interrupt()停止线程。这里介绍三种方法,话不多说,直接上代码。运行结果: (2)、使用AtomicBoolean(原子更新的布尔值)实现线程中断运行结果: (3)、使用Thread.currentThread()原创 2022-06-23 17:29:39 · 1137 阅读 · 0 评论 -
volatile工作原理学习总结
一、概述在多线程并发编程中synchronized和volatile都扮演着重要的角色,volatile是轻量级的synchronized,它在多处理器开发中保证了共享变量的 "可见性"。可见性的意思是当一个线程修改共享变量时,另外一个线程能读到这个修改的值。如果volatile变量修饰符使用恰当的话,它比synchronized的使用和执行成本更低,因为它不会引起线程上下文切换和调度。本篇文章我们将深入分析volatile关键字的原理,帮助我们正确使用volatile变量。由于volatile关键字与原创 2021-05-14 09:47:03 · 502 阅读 · 2 评论 -
JDK6中synchronized优化之自旋锁、锁擦除、锁粗化
一、概述前面一篇文章总结了synchronized在JDK1.6中其中一个优化-锁升级。除了锁升级的优化,JDK官方还引入了自旋锁、自适应自旋锁、锁擦除、锁粗化,本篇文章将挨个介绍这些优化,最后会给出一些我们平时使用synchronized实现同步锁需要注意的地方。原创 2021-05-10 16:35:36 · 346 阅读 · 0 评论 -
JDK6中synchronized优化之锁升级
目录一、概述二、CAS概述和作用三、synchronized锁升级过程四、偏向锁五、轻量级锁六、重量级锁七、锁的优缺点对比八、总结一、概述在JDK1.6之前,synchronized的性能比较差,在JDK1.6中,JDK官方对synchronized进行了一些优化,比如锁升级、锁消除等等。这些优化很多都涉及到CAS操作,了解了CAS,有利于我们理解synchronized底层锁升级的过程,话不多说,先看下什么是CAS?二、CAS概述和作用CAS的全称是: Co原创 2021-05-10 11:05:40 · 320 阅读 · 0 评论 -
synchronized工作原理剖析(二)
目录一、概述二、通过反汇编分析synchronized原理三、synchronized与Lock的区别四、synchronized锁对象存在哪里?五、总结一、概述前面一篇文章主要介绍了synchronized与并发编程三个特点:原子性、有序性、可见性的关系。本篇文章将通过反汇编的形式去分析一下synchronized的工作原理。二、通过反汇编分析synchronized原理我们编写一个简单的synchronized代码,如下:/** * 观察synchronize原创 2021-05-09 09:03:38 · 236 阅读 · 0 评论 -
synchronized工作原理剖析(一)
目录一、概述二、并发编程中的三个问题三、Java内存模型(JMM)四、synchronized保证三大特性五、synchronized的特性六、总结一、概述大家都知道,Synchronized主要用于并发编程中保证共享资源的安全,举个例子,12306的票不能超卖、商品库存不能超卖等问题,就可以Synchronized关键字来保证线程安全。同时并发编程也是目前工作中一个比较棘手的问题,也是面试中经常被问到的一个问题。synchronized的使用可能大部分小伙伴都会,但是对原创 2021-05-08 20:44:25 · 302 阅读 · 0 评论 -
并发编程常见面试题总结五
一、请谈谈volatile有什么特点,为什么它能保证变量对所有线程的可见性?当一个变量被volatile修饰后,具备两个特性:保证此变量对所有线程的可见性,当一条线程修改了这个变量的值,新值对于其他线程是可以立即得知的,而普通变量做不到这一点。 禁止指令重排序优化,普通变量仅仅能保证在方法执行过程中,得到正确结果,但是不保证程序代码的执行顺序。内存模型定义了8种内存间操作来保证可见性:...原创 2020-04-05 20:08:22 · 507 阅读 · 0 评论 -
并发编程常见面试题总结四
一、Java中的线程池是如何实现的?在Java中,所谓的线程池中的线程,其实是被抽象为了一个静态内部类Worker,基于AQS实现,存放在线程池的HashSet workers成员变量中; 需要执行的任务存放在成员变量workQueue中,workQueue是一个阻塞队列; 线程池的基本思想就是:从workQueue队列中不断取出需要执行的任务,放在Workers中进行执行;二、如何自定...原创 2020-04-05 20:01:24 · 400 阅读 · 0 评论 -
并发编程常见面试题总结三
一、ReentrantLock是如何实现可重入的?ReentrantLock内部自定义了同步器Sync,其实就是加锁的时候通过CAS算法,将线程对象放到一个双向链表中,每次获取锁的时候,看下当前维护的那个线程ID和当前请求的线程ID是否一样,一样就可重入。二、请说说CyclicBarrier和CountDownLatch的异同?CountDownLatch 是不可以重置的,所以无法重...原创 2020-04-05 19:53:10 · 335 阅读 · 0 评论 -
并发编程常见面试题总结二
一、什么是锁消除和锁粗化?锁消除:指虚拟机即时编译器在运行时,对一些代码上要求同步,但被检测到不可能存在共享数据竞争的锁进行消除。 锁粗化:原则上,同步块的作用范围应该尽可能的小,也就是说锁的粒度要尽可能小一点。但是如果一系列的连续操作都对同一个对象反复加锁和解锁,甚至加锁操作在循环体内,频繁地进行互斥同步也会导致不必要的性能损耗,锁粗化就是增大锁的作用范围。二、为什么说Synchroni...原创 2020-04-05 19:44:42 · 409 阅读 · 0 评论 -
并发编程常见面试题总结一
一、Synchronized用过么?其原理是什么?Synchronized是由JVM虚拟机实现的一种实现互斥同步的方式,被Synchronized修饰后的程序块编译后的字节码文件中,在编译前后被编译器生成了monitorenter和monitorexit两个字节码指令。在虚拟机执行到monitorenter指令时,首先要尝试获取对象的锁,如果这个对象没有锁定,或者当前线程已经拥有了这个对象...原创 2020-04-05 19:31:03 · 436 阅读 · 0 评论 -
并发编程学习之AQS抽象队列同步器
一、简介AQS是AbstractQueuedSynchronizer的简写,翻译过来就是:抽象队列同步器。AbstractQueuedSynchronizer在java.util.concurrent.locks包中,声明如下:public abstract class AbstractQueuedSynchronizerextends AbstractOwnableSynchroni...原创 2020-03-14 08:28:25 · 350 阅读 · 0 评论 -
并发编程学习之ForkJoinPool分支合并
一、简介JDK7引入了一种新的并发框架 - Fork/Join Framework分支合并框架,同时引入了一种新的线程池ForkJoinPool@sun.misc.Contendedpublic class ForkJoinPool extends AbstractExecutorService { }ForkJoinPool 是ExecutorService的补充,在某...原创 2020-03-13 20:15:50 · 417 阅读 · 0 评论 -
并发编程学习之线程池工作原理
一、简介上一篇文章介绍了各种线程池的使用、优势等,本篇我们将去了解线程池底层一点的相关知识。二、线程池底层原理Executor为我们提供了功能各异的线程池,其实其内部很多都是由ThreadPoolExecutor实现的,我们详细了解下ThreadPoolExecutor实现原理不但对我们使用理解Executor提供的线程池大有帮助,也让我们能根据实际情况自定义特定的线程池。我们先...原创 2020-03-12 19:31:15 · 359 阅读 · 0 评论 -
并发编程学习之线程池
一、简介首先,我们先了解一下为什么要用线程池?很多年以前,单核CPU的时候,多线程其实是假的,只是线程之间高速切换造成的“多线程”假象。现如今,基本上都是多核CPU电脑,多个线程各自跑在独立的CPU上,不用切换,效率比较高。线程池的主要特点:线程可复用; 控制最大并发数; 管理线程;线程池的优势:线程池主要是控制运行的线程数量,处理过程中将任务加入队列,然后在线程创建后启...原创 2020-03-11 19:46:15 · 229 阅读 · 0 评论 -
并发编程学习之ConcurrentHashMap扩容机制
一、简介在ConcurrentHashMap中,比较复杂部分就是其扩容机制,因为涉及到多个线程分工合作完成数据迁移和key的rehash操作。二、扩容思路ConcurrentHashMap扩容一般分为两个步骤:【a】Node<K,V>[] table数组的扩容,一般是扩大到原来数组大小的两倍; 【b】key的rehash以及数据的迁移:因为计算key在桶中的索引ind...原创 2020-03-09 21:15:32 · 1558 阅读 · 1 评论 -
并发编程学习之JDK1.8的ConcurrentHashMap
一、简介ConcurrentHashMap是线程安全的HashMap,声明如下:public class ConcurrentHashMap<K,V> extends AbstractMap<K,V> implements ConcurrentMap<K,V>, SerializableConcurrentHashMap相关类图如下:...原创 2020-03-09 21:06:48 · 257 阅读 · 0 评论 -
并发编程学习之CopyOnWriteArraySet
一、简介CopyOnWriteArraySet是线程安全的无序集合,可以将它理解成线程安全的HashSet。CopyOnWriteArraySet和HashSet都继承于共同的父类AbstractSet;但是,HashSet是通过“散列表(HashMap)”实现的,而CopyOnWriteArraySet则是通过上一节刚介绍的CopyOnWriteArrayList写时复制ArrayList实...原创 2020-03-06 22:06:26 · 522 阅读 · 0 评论 -
并发编程学习之写时复制CopyOnWriteArrayList
一、简介CopyOnWriteArrayList是JDK1.5时J.U.C引入了一个新的集合工具类,方便在并发环境下使用“列表”.public class CopyOnWriteArrayList<E>extends Objectimplements List<E>, RandomAccess, Cloneable, SerializableCopyO...原创 2020-03-06 22:01:43 · 410 阅读 · 0 评论 -
并发编程学习之延时队列DelayQueue
一、简介DelayQueue是JUC提供的一种无界延迟队列,它实现了BlockingQueue<E>阻塞队列接口,底层基于已有的PriorityBlockingQueue实现,类声明如下:public class DelayQueue<E extends Delayed>extends AbstractQueue<E>implements Bloc...原创 2020-03-05 22:21:20 · 776 阅读 · 4 评论 -
并发编程学习之阻塞队列ArrayBlockingQueue
一、简介ArrayBlockingQueue是一个有界阻塞队列,底层基于数组来实现的。这个队列对元素FIFO(先进先出)排序。队列的头是队列中存在时间最长的元素。队列的尾部是队列中时间最短的元素。新元素插入到队列的尾部,队列检索操作获取队列头部的元素。这是一个典型的“有界缓冲区”,其中大小固定的数组保存由生产者插入并由消费者提取的元素。一旦创建,容量就不能更改。试图将一个元素放入一个满...原创 2020-03-04 21:13:23 · 533 阅读 · 0 评论 -
并发编程学习之阻塞队列BlockingQueue和LinkedBlockingQueue
一、简介BlockingQueue,指的是阻塞队列,所谓队列,就是先进先出的一种数据结构。在Java中,BlockingQueue是一个接口,并且继承与Queue<E>接口,类图大体如下:目前已知的实现类有:ArrayBlockingQueue,DelayQueue,LinkedBlockingDeque,LinkedBlockingQueue,LinkedTr...原创 2020-03-03 20:55:49 · 482 阅读 · 0 评论 -
并发编程学习之原子变量类
一、简介在多线程环境下,如果多个线程需要对共享资源同时进行操作的话,很容易出现数据不一致的情况。通常情况下我们会使用synchronized同步方式来保证线程安全。从JDK 1.5开始提供了java.util.concurrent.atomic包,这个包中的原子操作类提供了一种用法简单、性能高效、线程安全地更新一个变量的方式。在java.util.concurrent.atomic包下...原创 2020-03-02 20:14:23 · 382 阅读 · 0 评论 -
并发编程学习之Condition和顺序访问
一、简介JUC提供了Lock可以方便的进行锁操作,但是有时候我们也需要对线程进行条件性的阻塞和唤醒,这时我们就需要Condition条件变量,可以方便的对持有锁的线程进行阻塞和唤醒。Condition将对象监视器方法(wait、notify和notifyAll)分解到不同的对象中,通过将它们与任意锁实现结合使用,实现每个对象具有多个等待集的效果。锁代替同步方法和语句的使用,Conditio...原创 2020-03-01 14:31:26 · 410 阅读 · 0 评论 -
并发编程学习之生产者消费者模式 - 使用Condition实现
一、简介上一篇我们介绍了使用传统的synchronized结合wait()/notifyAll()线程通信机制实现了生产者消费者案例,并且介绍了多线程交互中常见的虚假唤醒现象。我们都知道,Lock同步锁其实可以代替synchronized完成同步功能,并且使用起来还没有那么复杂,本文将介绍如何使用Lock实现生产者消费者案例。下表是synchronized和Lock实现线程通信方法的区别:...原创 2020-03-01 14:28:11 · 800 阅读 · 0 评论 -
并发编程学习之生产者消费者模式 - 使用Synchronized同步锁方式
一、简介生产者消费者问题是线程模型中的经典问题,生产者和消费者在同一时间段内共用同一存储空间,生产者向空间里生产数据,而消费者取走数据。本文我们将总结通过wait()和notify()多线程通信来实现生产者-消费者模式。wait():阻塞线程,将线程加入到等待队列中,会释放锁; notify()/notifyAll():唤醒一个或者多个等待队列中的线程,不会释放锁;二、实现示例...原创 2020-03-01 14:23:53 · 367 阅读 · 0 评论 -
并发编程学习之Lock同步锁
一、简介引出Lock同步锁之前,先了解一下synchronized同步的一些缺陷:如果一段代码被synchronized锁住,那么当一个线程获取了对应的锁,并执行该代码块时,其他线程便只能一直等待,等待获取锁的线程释放锁。如果某个时刻获得锁的线程发生阻塞现象,那么这把锁会被它一直持有,而其他线程永远无法获取锁,正常来说,不能让其他线程永远在那里等待。使用Lock锁的话,提供了一种机制可...原创 2020-02-29 10:25:19 · 543 阅读 · 0 评论 -
并发学习之CyclicBarrier循环栅栏
一、简介前面已经简单介绍了CountDownLatch闭锁,本文的CyclicBarrier其实跟闭锁差不多,当然还是存在一些区别。官网介绍如下:CyclicBarrier是一种同步辅助工具,允许一组线程彼此等待到达一个共同的障碍点。CyclicBarrier在包含固定大小的线程的程序中非常有用,这些线程有时必须彼此等待。这个屏障被称为循环屏障,因为它可以在等待的线程被释放后重新使用。...原创 2020-02-29 09:00:13 · 660 阅读 · 0 评论 -
并发编程学习之volatile关键字
一、简介volatile,是Java中的一个关键字。被volatile修饰的变量,在多个线程中保持可见性,注意,volatile不保证原子性,这也是volatile与synchronized的区别之一。那么什么是可见性呢?可见性是指当多个线程访问同一个变量时,一个线程修改了这个变量的值,其他线程能够立即看得到修改的值。要了解volatile的工作原理,首先需要了解一下Java内存模...原创 2020-02-27 19:51:12 · 294 阅读 · 0 评论 -
并发编程学习之Callable接口
一、简介Callable接口,其实跟Runnable接口的使用差不多,只不过Callable接口可以有返回值,返回结果并可能引发异常的任务。但是,Runnable不返回结果,也不能抛出checked异常。二、源码@FunctionalInterfacepublic interface Callable<V> { /** * Computes a res...原创 2020-02-26 20:11:50 · 455 阅读 · 0 评论 -
并发编程学习之线程8锁
一、简介所谓线程八锁,其实就是就是线程锁的8种情况,对应于是否加上synchronized,是否加上static等8种常见情况,具体见下面详解。二、线程8锁第一种情况: 两个线程调用同一个对象的两个普通同步方法,先打印one还是two?/** * 线程八锁第一种情况: 两个线程调用同一个对象的两个普通同步方法,先打印one还是two? * <p> * 运行结果: ...原创 2020-02-26 20:03:20 · 739 阅读 · 3 评论