
并发编程专栏
文章平均质量分 85
Java面试365
为什么每次都是差一点差一点,因为每次做事情都是差不多差不多
展开
-
Phaser并发阶段器
Phaser并发阶段器Phaser由JDK1.7提出,是一个复杂强大的同步辅助类,是对同步工具类CountDownLatch和CyclicBarrier的综合升级,能够支持分阶段实现等待的业务场景。我们可以回忆下CountDownLatch讲的是先指定N个线程,在N个线程干完活之前,其它线程都需要等待(导游等待旅游团所有人上车才能开车),而CyclicBarrier讲的是先指定N个线程。等N个线程到齐了大家同时干活(多个驴友相约去旅游,先到的需要等待后来的),而Phaser是两者的结合,可以理解为先指定N个原创 2022-03-26 23:50:33 · 5874 阅读 · 0 评论 -
Disruptor一个高性能队列
Disruptor一个高性能队列前言说到队列比较熟悉的可能是ArrayBlockingQueue、LinkedBlockingQueue这两个有界队列,大多应用在线程池中使用能保证线程安全,但其安全性都是通过ReentrantLock实现,而锁的效率较低,所以这里引出高性能的Disruptor队列。Disruptor对速度的把控只能说NB,Disruptor官网也是牛逼哄哄的这样描述At LMAX we have built an order matching engine, real-time原创 2022-03-24 10:04:59 · 772 阅读 · 0 评论 -
JAVA实现简单限流器(下)
JAVA实现简单限流器(下)Guava 如何实现令牌桶算法既然上篇提到采用定时任务有可能产生误差,那么Guava还能如何去实现呢?Guava采用巧妙的记录并动态计算下一令牌发放的时间,来实现令牌桶算法,如下说明。假设存在令牌桶的最大值1,流速为1个/秒,如果在当前T1时刻令牌桶没有令牌,那么请求正好在T1来临,下一次令牌发送时间应该是第3秒的位置由于在线程T1到达没有令牌,那么需要等待第3秒产生令牌后才能马上获取,那下一次产生令牌的时间就应该往后面移动一秒,也就是第4秒产生。假设这时T1刚刚原创 2022-03-23 21:00:01 · 988 阅读 · 0 评论 -
JAVA实现简单限流器(上)
JAVA实现简单限流器什么是限流器在高并发的场景下,出于对系统的保护会对流量进行限制。信号量实现限流器提到限流器的实现方式,很容易可以想到信号量是与之类似的原理,都是允许一定数量的线程访问临界区,具体实现代码如下所示,同一时刻只允许两个线程访问临界区域,其它线程等待实现限流目的。// 定义信号量对象 指定允许同时访问临界区的线程数Semaphore semaphore = new Semaphore(2);ExecutorService executorService = Executors原创 2022-03-21 23:19:51 · 3042 阅读 · 1 评论 -
并发生产者消费者模式
并发生产者消费者模式前言引入并发分工问题可以采用三大模式解决,Thread-Pre-Message模式、Worker Thread模式另外一种就是生产者消费者模式,这种模式的核心其实就是任务队列(阻塞队列),如下所示。只要涉及到异步编程在生产上我们一般都会使用线程池来执行业务,其实线程池的本质就是生产者消费者模式,不过我们需要注意的是线程池是消费者,调用线程池的线程是生产者,那么这种模式有什么优势呢?生产者消费者模式优势生产者消费者模式在Java中的实现就是线程池,那么这有何优势呢?生产者线原创 2022-03-18 14:29:08 · 653 阅读 · 0 评论 -
两阶段线程终止模型
两阶段线程终止模型前言引入线程终止主要应对的场景是一些服务只做阶段性任务的处理,处理完毕就可以终止线程,如项目中有可能使用到的数据迁移服务,使用时间较短,使用完毕就会将线程终止,那么如何去终止一个线程呢?这时肯定有人会脱口而出stop(),线程Thread提供的一个方法,这个方法确实可以终止线程但是带来的后果就是一剑封喉不给任何机会,一个业务处理到一半直接stop就有可能导致业务错乱,那么如何优雅的终止线程呢?两阶段终止模型线程终止最优雅的方式就是采用两阶段终止模型来处理,何为两阶段终止模型呢?结原创 2022-03-16 23:56:36 · 376 阅读 · 0 评论 -
并发分工问题的解决模式
并发分工模式前言引入并发三大问题就是互斥、同步、分工,这三大问题JAVA都提供了解决方案,如互斥可以使用互斥锁解决,同步可以采用管程原语解决,分工都是采用Fork/join、线程池解决等等,不过这些都是微观方面,如何从宏观层面去了解解决这些问题呢?这里以分工为例。分工的解决方案在并发编程中有很多模式如Thread-Per-Message模式,Worker Thread 模式等等这里将这两个模式拆开进行对比理解。Thread-Per-Message模式Thread-Per-Message模式可以从现原创 2022-03-16 00:10:45 · 235 阅读 · 0 评论 -
等待唤醒规范化之Guarded Suspension模式
Guarded Suspension模式什么是Guarded Suspension模式Guarded Suspension直译为保护性挂起,其核心是一个受保护的方法,该方法在执行其所需要真正执行的操作时需要满足特定的条件,当条件状态不满足时,执行受保护方法的线程挂起并进入等待状态,直到条件状态满足该线程才能继续执行。现实场景在我们生活中其实有很多这种场景例如,我们去外面用餐提前在网上预定了一个包间,然后到时间过去用餐,找到大堂经理这时经理发现包间还没收拾,就叫服务员马上收拾,让我们稍等片刻,大堂经理原创 2022-03-14 19:46:24 · 406 阅读 · 0 评论 -
ThreadLocal本地存储保证并发安全
ThreadLocal本地存储保证并发安全前言引入多线程因为并发执行带来了性能上的优势,同时也因为多线程间的数据竞争导致线程安全问题,我之前有提过可以利用不变性类Immutability来解决线程安全问题,这个办法的本质是让线程不直接修改属性值来保证线程安全,其实还有一种办法那就是线程间不共享,各自读写各自线程的变量,没有共享便没有了伤害,这就是本地存储方案ThreadLocal的优势所在。什么是ThreadLocalThreadLocal其实就是一种线程封闭的思想,本质有点像局部变量,所有的局部变原创 2022-03-12 11:39:30 · 1304 阅读 · 1 评论 -
利用不变性解决并发问题
利用不变性解决并发问题不变性模式我们知道并发最容易产生线程不安全的问题,主要原因是存在数据竞争,如果多个线程对同一个变量只读不修改那么就不存在线程安全问题,这种思想其实很简单,但也是最容易被我们忽略,利用这种思想就衍生出了一种模式-不变性模式也称为Immutability,简单描述就是一个对象创建后,它的状态就不会发生改变。不变性类不可变性类定义在Java中描述一个对象不可变一般采用final修饰,那么不可变性类也是如此,只要将类的属性全部采用fianl修饰,并且只允许方法只读那么这个类就是不可变原创 2022-03-11 00:45:30 · 604 阅读 · 0 评论 -
Fork/Join(JAVA版MapReduce)
Fork/Join(JAVA版MapReduce)分治思想接触过大数据的同学都应该了解过大数据知名计算框架MapReduce,MapReduce采用任务分解,结果合并的方式简单方便的完成大数据编程和计算处理,对于我们JAVA而言同样也是有类似计算处理框架这就是Fork/Join。Fork/Join的这种思想称之为分治思想,分而治之将一个大任务拆分为多个子任务,将子任务再进行拆分直到无法拆分可以求解,再将所有的子任务结果合并,这就是分治思想。Fork/JoinFork/Join这个计算框架中For原创 2022-03-09 21:47:55 · 472 阅读 · 0 评论 -
CompletionService批量异步执行
CompletionService批量异步执行前景引入我们知道线程池可以执行异步任务,同时可以通过返回值Future获取返回值,所以异步任务大多数采用ThreadPoolExecutor+Future,如果存在如下情况,需要从任务一二三中获取返回值后,保存到数据库中,用异步逻辑实现代码应该如下所示。public static void main(String[] args) throws ExecutionException, InterruptedException { ExecutorSe原创 2022-03-07 20:05:42 · 523 阅读 · 0 评论 -
CompletableFuture异步编程
CompletableFuture异步编程场景引入只要提到多线程来优化性能,那么必定离不开异步化,异步化的出现才是多线程优化性能这个核心方案的基础。异步化其实我们早已接触,如下Thread类,主线程不需要等待线程T1,T2的执行结果,就能实现异步逻辑。public static void main(String[] args) { Thread T1 = new Thread(()->{ // 执行方法A逻辑 }); Thread T2 = new T原创 2022-03-05 22:20:12 · 1139 阅读 · 0 评论