
Java多线程
文章平均质量分 71
修 己
这个作者很懒,什么都没留下…
展开
-
Java 一文讲清楚 CompletableFuture
当需要批量提交异步任务的时候建议使用CompletionService。CompletionService将线程池Executor和阻塞队列BlockingQueue的功能融合在了一起,能够让批量异步任务的管理更简单。CompletionService能够让异步任务的执行结果有序化。先执行完的先进入阻塞队列,利用这个特性,你可以轻松实现后续处理的有序性,避免无谓的等待,同时还可以快速实现诸如Forking Cluster这样的需求。线程池隔离。原创 2023-08-02 11:16:54 · 356 阅读 · 0 评论 -
Java基础面试~~多线程
1. 并行和并发有什么区别?并行:就是多个任务真实的同时执行。并发:偏重于多个任务交替执行,而多个任务之间有可能还是串行的。2. 线程和进程的区别?简而言之,进程是程序运行和资源分配的基本单位,一个程序至少有一个进程,一个进程至少有一个线程。进程在执行过程中拥有独立的内存单元,而多个线程共享内存资源,减少切换次数,从而效率更高。线程是进程的一个实体,是cpu调度和分派的基本单位,是比程序更小的能独立运行的基本单位。同一进程中的多个线程之间可以并发执行。3. 守护线程是什么?守护线程(原创 2021-08-19 09:54:35 · 1875 阅读 · 0 评论 -
JUC ~~ ReentrantLock 详解
1 介绍重入锁ReentrantLock,顾名思义,就是支持重进入的锁,它表示该锁能够支持一个线程对资源的重复加锁。除此之外,该锁的还支持获取锁时的公平和非公平性选择。1.1 重入锁的原理每一个锁关联一个线程持有者和计数器,当计数器为 0 时表示该锁没有被任何线程持有,那么任何线程都可能获得该锁而调用相应的方法;当某一线程请求成功后,JVM会记下锁的持有线程,并且将计数器置为 1;此时其它线程请求该锁,则必须等待;而该持有锁的线程如果再次请求这个锁,就可以再次拿到这个锁,同时计数器会递增;当线程退出同原创 2021-08-13 10:06:24 · 385 阅读 · 0 评论 -
JUC ~~ CyclicBarrier 详解
1 介绍CountDownLatch 在解决多个线程同步方面相对于join方法己经有了不少优化,但是CountDownLatch的计数器是一次性的,也就是等到计数器值变为0后,再调用CountDownLatch的await 和countdown 方法都会立刻返回,这就起不到线程同步的效果了。所以为了满足计数器可以重置的需要,JDK开发组提供了CyclicBarrier类。可以让一组线程全部达到一个状态后再全部同时执行,执行完毕之后重置CyclicBarrier的状态可以被重用。之所以叫做屏障是因为线程调用原创 2021-08-11 09:53:01 · 624 阅读 · 0 评论 -
JUC ~~ CountDownLatch 详解
1 案例介绍在日常开发中经常会遇到需要在主线程中开启多个线程去并行执行任务, 并且主线程需要等待所有子线程执行完毕后再进行汇总的场景。在CountDownLatch 出现之前一般都使用线程的join( )方法来实现这一点,但是join 方法不够灵活, 不能够满足不同场景的需要,所以JDK 开发组提供了CountDownLatch 这个类。1.1 Java中join()方法的理解thread.Join把指定的线程加入到当前线程,可以将两个交替执行的线程合并为顺序执行的线程。比如在线程B中调用了线程A的J原创 2021-08-10 09:42:48 · 340 阅读 · 0 评论 -
记一次线程池的故障,使用线程池该如何处理异常?
1 业务背景点赞业务:之前公司各个业务线的的点赞记录只存一条记录到数据库,并没有汇总每个资源的点赞总数,这样的话等到缓存失效时候,就需要去数据库中进行count()查询。随着数据量越来越大,count()的成本肯定会越来越高。所以想通过程序计算总数写入数据库的一张新表。等到缓存失效之后,用这张表的数据进行兜底做被动缓存。由于目前的数据量在9800多万,如果一条一条的进行同步计算,耗费的时间比较长,所以就用异步的方式,同时去处理不同业务线的数据。采用for循环的方式一次从数据库中查出500条数据进行处理原创 2021-08-06 09:58:10 · 853 阅读 · 0 评论 -
项目中如何合理的使用线程池~
1、使用线程池的好处?1、降低资源消耗:通过重复利用已创建的线程降低线程创建和销毁造成的消耗。2、提高响应速度:当任务到达时,可以不需要等待线程创建就能立即执行。3、提高线程的可管理性:线程是稀缺资源,如果无限制的创建,不仅会消耗系统资源,还会降低系统的稳定性。2、创建线程池的方式2.1 ExecutorsnewSingleThreadPoll() 创建一个只有一个线程的线程池。newFixedThreadPool(int numOfThreads)来创建固定线程数的线程池。newCache原创 2021-08-04 14:10:04 · 1544 阅读 · 0 评论 -
一张脑图帮你 复习 synchronized 关键字
一起讨论,一起进步。互联网打工人~原创 2021-07-22 09:54:19 · 336 阅读 · 0 评论 -
再用一张 脑图 讲解 volatile 关键字
原创 2021-07-21 09:48:16 · 218 阅读 · 0 评论 -
一张脑图解析 ConcurrentHashMap 的重点知识点
欢迎在评论区交流~ 一起学习 一起进步。原创 2021-07-19 10:33:05 · 270 阅读 · 0 评论 -
一张脑图解析 CopyOnWriteArrayList 的底层原理
欢迎在评论区交流,共同学习,一起进步~原创 2021-07-15 08:05:45 · 274 阅读 · 0 评论 -
用一张 脑图 解析 HashMap 的面试点
从上面的脑图中我们可以很详细的了解到HashMap的大部分知识点了,欢迎在评论区补充交流。原创 2021-07-13 09:46:56 · 299 阅读 · 0 评论 -
Java并发包中原子操作类原理剖析
1 介绍JUC 包提供了一系列的原子性操作类,这些类都是使用非阻塞算法CAS 实现的,相比使用锁实现原子性操作这在性能上有很大提高。所有的原子性操作类的原理都大致相同。2 原子变量操作类JUC 并发包中包含有Atomiclnteger 、AtomicLong 和AtomicBoolean 等原子性操作类,它们的原理类似,下面讲解AtomicLong 类。AtomicLong 是原子性递增或者递减类,其内部使用Unsafe 来实现,我们看下面的代码。/** * A {@code long} valu原创 2021-07-05 16:55:37 · 203 阅读 · 0 评论 -
volatile为什么能禁止指令重排 ??
1 什么是指令重排?Java 内存模型允许编译器和处理器对指令重排序以提高运行性能, 并且只会对不存在数据依赖性的指令重排序。在单线程下重排序可以保证最终执行的结果与程序顺序执行的结果一致,但是在多线程下就会存在问题。int i = 1; //(1)int j = 2; //(2)int k = i + j; //(3)如上代码,变量K的值依赖 i 和 j 的值,所以重排序后能操作 (3) 的操作在 1,2之后。1和2谁先执行就不一定了,不过在单线程中不会有什么问题,下面看一个多线程的例子:p原创 2021-07-02 09:35:43 · 1638 阅读 · 0 评论 -
什么场景下我们会用到阻塞队列??
1 常见的阻塞队列1 LinkedBlockingQueueLinkedBlockingQueue 的内部是通过单向链表实现的游街队列(默认为Integer的最大值),使用头、尾节点来进行入队和出队操作,也就是入队操作都是对尾节点进行操作,出队操作都是对头节点进行操作。如下图所示,对头、尾节点的操作分别使用了单独的独占锁从而保证了原子性,所以出队和入队操作是可以同时进行的。另外对头、尾节点的独占锁都配备了一个条件队列,用来存放被阻塞的线程,并结合入队、出队操作实现了一个生产消费模型。详细地址:ht原创 2021-07-01 14:49:34 · 2247 阅读 · 0 评论 -
java容器~面试知识点整理
一、导图二、详解2.1 List2.1.1 ArrayListArrayList的底层数据结构就是一个数组,数组元素的类型为Object类型,对ArrayList的所有操作底层都是基于数组的。ArrayList的线程安全性:对ArrayList进行添加元素的操作的时候是分两个步骤进行的,这个过程在多线程的环境下是不能保证具有原子性的,因此ArrayList在多线程的环境下是线程不安全的 。2.1.2 LinkedListLinkedList 的底层数据结构是双向链表。2.1.3 数组和链表原创 2021-06-28 13:54:02 · 162 阅读 · 0 评论 -
简单设计秒杀系统
1 秒杀架构图2 秒杀场景登陆12306进行火车票抢座1599元购入飞天茅台周董演唱会的门票双十一秒杀活动3 秒杀的难点瞬时高并发流量的挑战超卖恶意攻击用户体验木桶短板理论,整个系统的瓶颈往往都在 DB4 如何设计上图是一个典型的互联网业务,用户完成一个写操作,一般会通过接入层和逻辑层,这里的服务都是无状态,可以通过平行拓展去解决高并发的问题;到了 db 层,必须要落到介质中,可以是磁盘/ssd/内存,如果出现 key 的冲突,会有一些并发控制技术,例如 cas/加锁/原创 2021-06-28 10:00:34 · 489 阅读 · 0 评论 -
synchronized 底层实现
0 大纲1 引言在多线程并发编程中Synchronized一直是元老级角色,很多人都会称呼它为重量级锁,但是随着Java SE1.6对Synchronized进行了各种优化之后,有些情况下它并不那么重了,下面介绍一下Java SE1.6中为了减少获得锁和释放锁带来的性能消耗而引入的偏向锁和轻量级锁,以及锁的存储结构和升级过程。2 术语定义术语英文说明CASCompare and Swap比较并设置。用于在硬件层面上提供原子性操作。在 Intel 处理器中,比较并交换通过转载 2021-06-18 10:22:30 · 232 阅读 · 4 评论 -
java面试整理~基础
一、进程和线程1.1 多进程进程是资源(CPU、内存等)分配的基本单位,它是程序执行时的一个实例。程序运行时系统就会创建一个进程,并为它分配资源,然后把该进程放入进程就绪队列,进程调度器选中它的时候就会为它分配CPU时间,程序开始真正运行。1.2 多线程线程是程序执行时的最小单位,它是进程的一个执行流,是CPU调度和分派的基本单位,一个进程可以由很多个线程组成,线程间共享进程的所有资源,每个线程有自己的堆栈和局部变量。线程由CPU独立调度执行,在多CPU环境下就允许多个线程同时运行。同样多线程也可以原创 2021-06-17 10:39:42 · 298 阅读 · 3 评论 -
Java并发之AQS详解(二)源码解析
1 介绍在Java并发之AQS详解(一)中,已经对AQS中主要的类,重点方法、流程进行了分析,本文针对List item独占方式的获取与释放资源、List item分享方式的获取去释放资源、List item入队与出队源码进行分析。...原创 2020-11-09 20:40:03 · 1182 阅读 · 5 评论 -
Java并发之AQS详解(一)
1 AQS产生背景通过JCP的JSR166规范,Jdk1.5开始引入了JUC包,这个包提供了一系列支持并发的组件。这些组件是一系列的同步器,这些同步器主要维护着以下几个功能:内部同步状态的管理(例如表示一个锁的状态是获取还是释放),同步状态的更新和检查操作,且至少有一个方法会导致调用线程在同步状态被获取时阻塞,以及在其他线程改变这个同步状态时解除线程的阻塞。上述的这些的实际例子包括:互斥排它锁的不同形式、读写锁、信号量、屏障、Future、事件指示器以及传送队列等。 几乎任一同步器都可以用来实现其他形原创 2020-10-27 17:01:07 · 826 阅读 · 3 评论 -
Java 中共享变量的内存可见性问题 + volatile + CAS
一、Java 中共享变量的内存可见性问题在多线程下处理共享变量时Java 的内存模型,如下图所示。Java 内存模型规定,将所有的变量都存放在主内存中,当线程使用变量时,会把主内存里面的变量复制到自己的工作空间或者叫作工作内存,线程读写变量时操作的是自己工作内存中的变量。Java 内存模型是一个抽象的概念,那么在实际实现中线程的工作内存是什么呢?请看图2-5 。图中所示是一个双核CPU 系统架构,每个核有自己的控制器和运算器,其中控制器包含一组寄存器和操作控制器,运算器执行算术逻辅运算。每个核都有原创 2020-10-09 21:40:39 · 1379 阅读 · 1 评论 -
Threadlocal(二)源码解析+面试题总结
一、面试题1 先说一下对threadlocal的理解吧?threadlocal对象可以提供线程局部变量,也就是说每个线程拥有一份自己的一个副本变量。多个线程之间互不干扰。一般会重写initialValue()方法来赋值。2 什么时候线程第一次给赋的值呢?每个线程第一次访问get的时候就会给线程赋值,它就会使用重写的initialValue方法分配数据。3 threadlocal原理 jdk1.8?java8是每一个线程对应的Threadlocal对象内部拥有一个threadlocals对象,th原创 2020-10-09 21:24:58 · 169 阅读 · 0 评论 -
Threadlocal(一)基础介绍
1.ThreadLocal1.1 介绍ThreadLocal 是JDK 包提供的,它提供了线程本地变量,也就是如果你创建了一个ThreadLocal 变量,那么访问这个变量的每个线程都会有这个变量的一个本地副本。当多个线程操作这个变量时,实际操作的是自己本地内存里面的变量,从而避免了线程安全问题。创建一个ThreadLocal 变量后,每个线程都会复制一个变量到自己的本地内存。1.2 实现原理ThreadLoacl set方法源码public void set(T value) { //获原创 2020-10-09 21:19:55 · 252 阅读 · 1 评论 -
扫盲篇之 ~线程的创建方式、线程的六个状态、何为线程死锁
一 线程三种基本创建方式1.1 继承Threadpublic class Demo1 { public static class MyThread extends Thread{ @Override public void run(){ System.out.println("创建线程"); } } public static void main(String[] args) { MyThre原创 2020-10-09 14:51:57 · 145 阅读 · 0 评论