![](https://img-blog.csdnimg.cn/20201014180756738.png?x-oss-process=image/resize,m_fixed,h_64,w_64)
JUC
文章平均质量分 56
微滑低
再见少年拉满弓,不惧岁月不惧风!
展开
-
自定义自旋锁及自旋锁的使用场景
学习地址:狂神Bilibili个人主页1.什么是自学锁?是指当一个线程在获取锁的时候,如果锁已经被其它线程获取,那么该线程将循环等待,然后不断的判断锁是否能够被成功获取,直到获取到锁才会退出循环。2.使用场景就像你去银行办理业务先去取号,在没轮到你之前你必须等待;直到银行办理人员叫你去办理业务,到你办理业务的时候这个窗口只能是你这个号码办理,其他号码不能跟你一起在这个窗口办理;办完业务后,办理任务再呼下一个号码3.自定义自旋锁import java.util.concurrent.atomic原创 2021-06-15 12:16:38 · 587 阅读 · 0 评论 -
Synchronized版和Lock版的可重入锁及使用场景
学习地址:狂神Bilibili个人主页1.什么是可重入锁?可重入锁指的是可递归调用的锁,也叫递归锁。在外层使用锁之后,在内层仍然可以使用,并且不发生死锁(前提得是同一个对象或者class),这样的锁就叫做可重入锁2.使用场景比如我今天遇到的一个场景:用户名和密码保存在本地txt文件中,则登录验证方法和更新密码方法都应该被加synchronized,那么当更新密码的时候需要验证密码的合法性,所以需要调用验证方法,此时是可以调用的。3.synchronized版的可重入锁import javax原创 2021-06-15 11:58:01 · 662 阅读 · 0 评论 -
Volatile详解
1.什么是Volatile?Volatile 是 Java 虚拟机提供轻量级的同步机制2.Volatile的特点保证可见性不保证原子性可避免指令重排3.如何保证可见性?3.1这里涉及JMM的8种操作3.2场景:两个线程同时进行,把主存中的共享变量加载到自己的工作内存中,但是B线程修改了共享变量,并放回到主内存中;此时A线程并可见,就会导致A线程阻塞3.3代码示例import java.util.concurrent.TimeUnit;public class JMMDem原创 2021-06-15 11:12:01 · 142 阅读 · 0 评论 -
线程池中如何定义最大线程数量?
Java自定义线程池来模拟银行办理业务场景来解析ThreadPoolExecutor的七大参数和四大拒绝策略上面博客中,我们的最大线程数量是自定义,但是通常情况下,我们并不会这么做。1.解决办法CPU密集型IO密集型2.什么是CPU密集型?比如让你(CPU)数一堆豆子(要执行的任务),在数的过程中,不就不能去干别的事情了;然后你把豆子分几堆来数,但是如果还是你自己数的话时间还是一样的;但是这个时间你让你的兄弟(其他CPU)来帮你一起数,那么就会很快数完豆子。这就是CPU密集型。所以你可以原创 2021-06-14 22:09:50 · 1056 阅读 · 0 评论 -
ReadWriteLock的使用
学习地址:狂神Bilibili个人主页1.什么是ReadWriteLock?ReadWriteLock(读写锁)维护一对关联的锁,一个用于只读操作一个用于写。在没有写线程的情况下一个读锁可能会同时被多个读线程 持有;写锁是独占的独占锁(写锁) 一次只能被一个线程占有共享锁(读锁) 多个线程可以同时占有2.没加读写锁代码示例import java.util.HashMap;import java.util.Map;import java.util.concurrent.locks.Lo原创 2021-06-14 21:17:05 · 163 阅读 · 0 评论 -
Semaphore的使用及原理
学习地址:狂神Bilibili个人主页1.什么是Semaphore?Semaphore中管理一组虚拟的许可,许可的初始数量可以通过构造函数指定。在操作时可以首先获得许可(只要还有剩余的许可),并且在使用以后释放许可。如果没有许可,那么acquire将阻塞直到有许可(或者直到被中断或者操作超时)。release方法将返回一个许可给信号量。2.理解场景抢车位3.代码示例import java.util.concurrent.Semaphore;import java.util.concu原创 2021-06-14 20:55:07 · 166 阅读 · 0 评论 -
CyclicBarrier的使用及与CountDownLatch的区别
1.什么是CyclicBarrier?CyclicBarrier字面意思是“可重复使用的栅栏”栅栏类似于闭锁,它能阻塞一组线程直到某个事件的发生。栅栏与闭锁的关键区别在于,所有的线程必须同时到达栅栏位置,才能继续执行。闭锁用于等待事件,而栅栏用于等待其他线程。CyclicBarrier 可以构造出一个集结点,当某一个线程执行 await() 的时候,它就会到这个集结点开始等待,等待这个栅栏被撤销。直到预定数量的线程都到了这个集结点之后,这个栅栏就会被撤销,之前等待的线程就在此刻统一出发,继续去执行剩下原创 2021-06-14 20:39:19 · 113 阅读 · 0 评论 -
CountDownLatch的使用及原理
学习地址:狂神Bilibili个人主页1.什么是CountDownLatch?一般被称作"计数器",作用大致就是数量达到了某个点之后计数结束,才能继续往下走。可以用作流程控制之类的作用,大流程分成多个子流程,然后大流程在子流程全部结束之前不动(子流程最好是相互独立的,除非能很好的控制两个流程的关联关系),子流程全部结束后大流程开始操作。2.使用场景一位教室管理员需要等学生走完了才能锁门,否则就会把学生关在里面3.代码示例import java.util.concurrent.CountDown原创 2021-06-14 20:25:47 · 174 阅读 · 0 评论 -
Callable与Runnable的区别及注意点
1.Callable与Runnable的区别有返回值可以抛出异常方法不同 call()2.使用区别Runnable使用new Thread(new Runnable()).start();Callable使用 直接放到Thread是不允许的,两者没有直接联系,但是它跟Runnable有联系(就像你想认识你女朋友的闺蜜一样),所以可以通过Runnable的FutureTask来建立联系3.代码实现import java.util.concurrent.Callable;原创 2021-06-14 15:16:27 · 478 阅读 · 0 评论 -
Lock版使用Condition来实现精准通知和唤醒线程
学习地址:狂神Bilibili个人主页1.概述之前说过,synchronized版不能实现精准通知和唤醒线程,所以就出现了Lock版2.Lock版使用Condition代码package com.kuang.pc;import java.util.concurrent.locks.Condition;import java.util.concurrent.locks.Lock;import java.util.concurrent.locks.ReentrantLock;/** *原创 2021-06-14 14:09:55 · 185 阅读 · 0 评论 -
Lock版生产者消费者问题及与synchronized版的比较
学习地址:狂神Bilibili个人主页1.解决生产者消费者问题三步骤等待唤醒业务通知唤醒2.代码package com.kuang.pc;import java.util.concurrent.locks.Condition;import java.util.concurrent.locks.Lock;import java.util.concurrent.locks.ReentrantLock;public class B { public static void m原创 2021-06-14 13:52:21 · 46 阅读 · 0 评论 -
synchronized实现生产者消费者通信问题及可能产生的虚假唤醒问题
文章目录1.解决生产者消费者问题三步骤2.代码(测试类、资源类)3.虚假唤醒问题5.原因分析6.问题解决学习地址:狂神Bilibili个人主页1.解决生产者消费者问题三步骤等待唤醒业务通知唤醒2.代码(测试类、资源类)/** * 线程交替执行 A B 操作同一个变量 num = 0 * A num+1 * B num-1 */public class A { public static void main(String[] args) { Da原创 2021-06-14 13:36:32 · 101 阅读 · 0 评论 -
浅谈Java的ForkJoin
1.什么是ForkJoin?ForkJoin是由JDK1.7后提供多线并发处理框架,ForkJoin的框架的基本思想是分而治之。使用ForkJoin将相同的计算任务通过多线程的进行执行。从而能提高数据的计算速度。通过多线程提高大数据的处理。处理大数据是使用ForkJoin的前提,数据较小时不建议使用!2.主要思想分而治之:ForkJoin将一个复杂的任务,按照设定的阈值进行分解成多个子任务,然后将各个子任务结果进行汇总。如图:当然实际就按阈值来拆分子任务3.使用使用ForkJoin框架,需要创建原创 2021-04-30 12:11:21 · 148 阅读 · 1 评论 -
Java自定义线程池来模拟银行办理业务场景来解析ThreadPoolExecutor的七大参数和四大拒绝策略
1.在阿里巴巴开发手册中指出不允许使用 Executors 去创建,而是通过 ThreadPoolExecutor 的方式,所以大部分我们都是使用ThreadPoolExecutor2.使用ThreadPoolExecutor 那么就得知道七大参数3.四种拒绝策略4.正常银行办理业务场景解析:这里只开了两个窗口办理业务,当客户来办理时只能在这两个窗口办理业务,人越来越多,就会在候客区等待,依次办理业务5.假设有一天要办理的客户超级多解析:当客户很多是,那么银行就会开启其他几个窗口,当窗原创 2021-04-29 20:36:30 · 246 阅读 · 0 评论 -
解决并发下的ArrayList不安全问题的几种办法
1.多线程的ArrayListpackage com.kuang.unsafe;import java.util.*;import java.util.concurrent.ConcurrentHashMap;import java.util.concurrent.CopyOnWriteArrayList;public class ListTest { public static void main(String[] args) { //并发下ArrayList 是不安原创 2021-04-29 15:56:07 · 565 阅读 · 7 评论 -
Synchronized和Lock的区别
针对同一个售票案例进行分析,两者都是解决并发所产生的问题Synchornized代码示例://售票public class SaleTicketDemo { public static void main(String[] args) { //并发:多个线程操作同一个资源,把资源类丢进线程里 Ticket ticket = new Ticket(); new Thread(()->{for (int i = 0; i < 40; i+原创 2021-04-27 22:02:21 · 140 阅读 · 0 评论 -
Stream流式计算及四大函数式接口
学习地址:狂神Bilibili个人主页1. 题目要求:只能用一行代码实现!现在有5个用户!筛选:1、ID 必须是偶数2、年龄必须大于23岁3、用户名转为大写字母4、用户名字母倒着排序5、只输出一个用户!2.使用Stream流式计算User类import lombok.AllArgsConstructor;import lombok.Data;import lombok.NoArgsConstructor;// 有参,无参构造,get、set、toString方法!@Data原创 2021-06-15 10:21:58 · 485 阅读 · 1 评论