
并发编程
并发编程
日薪灬越亿
这个作者很懒,什么都没留下…
展开
-
java并发编程(二十四)-并发安全之活锁,线程饥饿
什么是活锁?多线程环境下,线程在尝试拿锁的机制中,发生多个线程之间互相谦让,不断发生拿锁,释放锁的过程。模拟银行转账的业务:实体类:package com.caojiulu;import java.util.concurrent.locks.Lock;import java.util.concurrent.locks.ReentrantLock;/** *@autho...原创 2019-05-09 17:32:26 · 176 阅读 · 0 评论 -
java并发编程(二十三)-并发安全之死锁
死锁资源一定是多于1个,同时小于等于竞争的线程数,资源只有一个,只会产生激烈的竞争。死锁的根本成因:获取锁的顺序不一致导致。死锁的一般情况:package com.caojiulu;import com.caojiulu.SleepTools;/** *@author caojiulu * *类说明:演示普通的死锁和解决 */public class No...原创 2019-05-09 17:07:15 · 140 阅读 · 0 评论 -
java并发编程(二十二)-并发安全的基本概念
类的线程安全定义如果多线程下使用这个类,不过多线程如何使用和调度这个类,这个类总是表示出正确的行为,这个类就是线程安全的。类的线程安全表现为:操作的原子性 内存的可见性不做正确的同步,在多个线程之间共享状态的时候,就会出现线程不安全。怎么才能做到类的线程安全?栈封闭所有的变量都是在方法内部声明的,这些变量都处于栈封闭状态。无状态没有任何成员变量的类,就叫无状...原创 2019-05-06 10:44:21 · 134 阅读 · 0 评论 -
java并发编程(二十一)-线程池CompletionService的使用(获取线程处理结果)
在我们日常使用线程池的时候,经常会有需要获得线程处理结果的时候。此时我们通常有两种做法。《Java并发编程实践》一书6.3.5节CompletionService:Executor和BlockingQueue,有这样一段话:"如果向Executor提交了一组计算任务,并且希望在计算完成后获得结果,那么可以保留与每个任务关联的Future,然后反复使用get方法,同时将参数timeout...原创 2019-05-05 19:00:46 · 905 阅读 · 0 评论 -
java并发编程(二十)-Executor框架
1.Executor框架主要由3大部分组成: 任务。包括被执行任务需要实现的接口:Runnable接口或者Callable接口 任务的执行。包括执行机制的核心接口Executor,以及继承Executor的ExecutorService接口。Executor框架有两个关键类,ThreadPoolExe...转载 2019-05-05 18:33:08 · 110 阅读 · 0 评论 -
java并发编程(十九)- 线程池(ScheduledThreadPoolExecutor )详细使用
多线程环境下需要定期执行周期任务,Timer不建议使用了。newSingleThreadScheduledExecutor:只包含一个线程,只需要单个线程执行周期任务,保证顺序的执行各个任务newScheduledThreadPool可以包含多个线程的,线程执行周期任务,适度控制后台线程数量的时候方法说明:schedule:只执行一次,任务还可以延时执行scheduleAtF...原创 2019-05-05 18:25:40 · 868 阅读 · 0 评论 -
java并发编程(十九)- 线程池(ThreadPoolExecutor)详细使用
线程池的创建ThreadPoolExecutor,jdk所有线程池实现的父类各个参数含义intcorePoolSize:线程池中核心线程数,<corePoolSize,就会创建新线程,=corePoolSize,这个任务就会保存到BlockingQueue,如果调用prestartAllCoreThreads()方法就会一次性的启动corePoolSize个...原创 2019-05-05 18:19:34 · 259 阅读 · 0 评论 -
java并发编程(十八)-通过阻塞队列实现一个自己的线程池
什么是线程池?为什么要用线程池?降低资源的消耗。降低线程创建和销毁的资源消耗; 提高响应速度:线程的创建时间为T1,执行时间T2,销毁时间T3,免去T1和T3的时间 提高线程的可管理性。实现一个我们自己的线程池线程必须在池子已经创建好了,并且可以保持住,要有容器保存多个线程; 2、线程还要能够接受外部的任务,运行这个任务。容器保持这个来不及运行的任务.pac...原创 2019-05-04 16:59:07 · 161 阅读 · 0 评论 -
java并发编程(十七)-阻塞队列(生产者与消费者模式)
概念、生产者消费者模式1)当队列满的时候,插入元素的线程被阻塞,直达队列不满。2)队列为空的时候,获取元素的线程被阻塞,直到队列不空。生产者和消费者模式生产者就是生产数据的线程,消费者就是消费数据的线程。在多线程开发中,如果生产者处理速度很快,而消费者处理速度很慢,那么生产者就必须等待消费者处理完,才能继续生产数据。同样的道理,如果消费者的处理能力大于生产者,那么消费者就必须等待...原创 2019-05-04 15:28:54 · 278 阅读 · 0 评论 -
java并发编程(十六)-并发容器后续(ConcurrentSkipListMap ConcurrentSkipListSet ConcurrentLinkedQueue 写时复制容器)
ConcurrentSkipListMap 和 ConcurrentSkipListSetTreeMap和TreeSet有序的容器,这两种容器的并发版本ConcurrentSkipListSet是线程安全的有序的集合,适用于高并发的场景。ConcurrentSkipListSet和TreeSet,它们虽然都是有序的集合。但是,第一,它们的线程安全机制不同,TreeSet是非线程安...原创 2019-05-03 21:48:46 · 326 阅读 · 0 评论 -
java并发编程(十六)-并发容器之ConcurrentHashMap (JDK1.8中原理和实现)
与1.7相比的重大变化取消了segment数组,直接用table保存数据,锁的粒度更小,减少并发冲突的概率。 存储数据时采用了链表+红黑树的形式,纯链表的形式时间复杂度为O(n),红黑树则为O(logn),性能提升很大。什么时候链表转红黑树?当key值相等的元素形成的链表中元素个数超过8个的时候。主要数据结构和关键变量Node类存放实际的key和value值。sizeCtl:负...原创 2019-05-03 21:02:10 · 235 阅读 · 0 评论 -
java并发编程(十六)-并发容器之ConcurrentHashMap (JDK1.7中原理和实现)
ConcurrentHashMap中的数据结构ConcurrentHashMap是由Segment数组结构和HashEntry数组结构组成。Segment实际继承自可重入锁(ReentrantLock),在ConcurrentHashMap里扮演锁的角色;HashEntry则用于存储键值对数据。一个ConcurrentHashMap里包含一个Segment数组,每个Segment里包含一个Ha...原创 2019-05-03 12:04:56 · 494 阅读 · 0 评论 -
java程序员必备的并发编程基础知识( hash以及位运算)
Hash散列,哈希:把任意长度的输入通过一种算法(散列),变换成为固定长度的输出,这个输出值就是散列值。属于压缩映射,容易产生哈希冲突。Hash算法有直接取余法等。产生哈希冲突时解决办法:开放寻址;2、再散列;3、链地址法(相同hash值的元素用链表串起来)。ConcurrentHashMap在发生hash冲突时采用了链地址法。md4,md5,sha-hash算法也属于hash算法...原创 2019-05-02 22:38:51 · 249 阅读 · 0 评论 -
利用位运算做权限控制
位运算应用范围十分广泛,下面这个例子就是用来做权限控制类似于linux的文件系统里面的chmod 777 节约内存空间,一个数据机构就能表示多种权限直接上代码吧:package com.caojiulu;/** *@author caojiulu * *类说明: */public class Permission { // 是否允许查询,二进制第1位...原创 2019-05-02 22:38:32 · 438 阅读 · 0 评论 -
java并发编程(十五)-LockSupport工具类
LockSupport是Java6引入的一个工具类,它简单灵活,应用广泛。一、简单俗话说,没有比较就没有伤害。这里咱们还是通过对比来介绍LockSupport的简单。在没有LockSupport之前,线程的挂起和唤醒咱们都是通过Object的wait和notify/notifyAll方法实现。写一段例子代码,线程A执行一段业务逻辑后调用wait阻塞住自己。主线程调用notify方...转载 2019-05-02 18:30:41 · 130 阅读 · 0 评论 -
java并发编程(十四)- 显示锁
使用显示锁的基本范式package com.caojiulu;import java.util.concurrent.locks.Lock;import java.util.concurrent.locks.ReentrantLock;/** * @author caojiulu * *使用显示锁的范式 */public class LockDemo { priva...原创 2019-05-02 18:02:38 · 144 阅读 · 0 评论 -
java并发编程(十三)- 显示锁使用Lock和Condition实现等待通知模式
通常在开发并发程序的时候,会碰到需要停止正在执行业务A,来执行另一个业务B,当业务B执行完成后业务A继续执行。ReentrantLock通过Condtion等待/唤醒这样的机制.相比较synchronize的wait()和notify()/notifAll()的机制而言,Condition具有更高的灵活性,这个很关键。Conditon可以实现多路通知和选择性通知。当使用notify()/n...原创 2019-05-02 17:57:43 · 274 阅读 · 0 评论 -
java并发编程(十二)- CAS(Compare And Swap)
什么是原子操作?"原子操作(atomic operation)是不需要synchronized",这是多线程编程的老生常谈了。所谓原子操作是指不会被线程调度机制打断的操作;这种操作一旦开始,就一直运行到结束,中间不会有任何 context switch (切[1]换到另一个线程)。CAS的原理利用了现代处理器都支持的CAS的指令,循环这个指令,直到成功为止。CAS(Compa...原创 2019-04-26 10:14:23 · 130 阅读 · 0 评论 -
java并发编程(十一)-常用的并发工具类
CountDownLatch 是一组线程等待其他的线程完成工作以后在执行,加强版join await用来等待,countDown负责计数器的减一package com.caojiulu;import java.util.concurrent.CountDownLatch;import com.caojiulu.SleepTools;/** *@author ...原创 2019-04-14 23:35:36 · 226 阅读 · 0 评论 -
java并发编程(十)-Deque 双端队列和工作密取
什么是 Deque?Deque是Double ended queue (双端队列)的缩写,读音和 deck 一样,蛋壳。Deque 继承自Queue,直接实现了它的有 LinkedList, ArayDeque, ConcurrentLinkedDeque 等。Deque 支持容量受限的双端队列,也支持大小不固定的。一般双端队列大小不确定。Deque 接口定义了一些从头...转载 2019-04-14 21:41:10 · 556 阅读 · 0 评论 -
java并发编程(九)-Fork/Join的使用
什么是分而治之?规模为N的问题,N<阈值,直接解决,N>阈值,将N分解为K个小规模子问题,子问题互相对立,与原问题形式相同,将子问题的解合并得到原问题的解Fork/Join 使用的标准范式示例:Fork/Join的同步用法同时演示返回结果值:统计整形数组中所有元素的和产生数据的工具类:package com.cajiulu;imp...原创 2019-04-14 23:03:17 · 1505 阅读 · 0 评论 -
java并发编程(八)-等待超时模式实现数据库连接池
什么是超时等待?调用一个方法时,等待一段时间(一般给定一个时间段),如果该方法能够在给定的时间段内得到结果,那么将结果立刻返回,反之,超时返回默认结果。这就是超时等待。等待和通知的标准范式:即加锁,条件循环和处理逻辑三个步骤,而这种范式无法做到超时等待。由于经典的等待/通知范式无法做到超时等待,也就是说,当消费者在获得锁后,如果条件不满足,等待生产者改变条件之前会一直处于等待状态...原创 2019-04-12 10:57:07 · 767 阅读 · 0 评论 -
java并发编程(七)-调用yield() 、sleep()、wait()、notify()等方法对锁有何影响?
yield:让出时间片,不会释放锁sleep:线程进入睡眠状态,不会释放锁wait:调动方法之前,必须要持有锁。调用了wait()方法以后,锁就会被释放,进入锁的等待队列,方法返回后重新拿到锁notify:调动方法之前,必须要持有锁,调用notify()方法本身不会释放锁的。而是通知等待队列中的某一个线程,同步代码块执行完毕后才会释放锁notifyAll:同notify,有一点不同...原创 2019-04-11 15:20:22 · 556 阅读 · 0 评论 -
java并发编程(六)-join()方法
先开门见山的给大家分享一道面试题面试题:有一个主线程,里面有三个子线程,想等三个子线程都执行完毕后,才执行主线程,怎么办?答案是使用多线程的join方法。线程A,执行了线程B的join方法,线程A必须要等待B执行完成了以后,线程A才能继续自己的工作代码分享如下:package com.caojiulu;/** * *@author caojiulu ...原创 2019-04-11 15:03:27 · 169 阅读 · 0 评论 -
java并发编程(五)-等待和通知的标准范式
借用网上的例子说明一下:一家人要吃午饭,妈妈做饭,我和爸爸吃饭。让我和爸爸的坐在桌子旁准备吃饭。但是我和爸爸又想多看一会电视,这个时候我们该怎么办呢?我们只能不断的跑到厨房看妈妈是不是做好饭了。while(food != done){ Thread.sleep(1000);}haveFood();通过以上的方式我们可以多看一会电视,并且避免了无效的等待,但是还是有点问题:...原创 2019-04-11 14:39:57 · 276 阅读 · 0 评论 -
java并发编程(四):synchronized关键字解析
synchronized一定要弄清楚,锁的对象是什么。对象锁,锁的是类的对象实例。类锁 ,锁的是每个类的的Class对象,每个类的的Class对象在一个虚拟机中只有一个,所以类锁也只有一个。...原创 2019-04-09 17:28:36 · 164 阅读 · 0 评论 -
java并发编程(四):volatile关键字解析
Java并发编程:volatile关键字解析 volatile这个关键字可能很多朋友都听说过,或许也都用过。在Java 5之前,它是一个备受争议的关键字,因为在程序中使用它往往会导致出人意料的结果。在Java 5之后,volatile关键字才得以重获生机。 volatile关键字虽然从字面上理解起来比较简单,但是要用好不是一件容易的事情。由于volatile关键字是与Java的内存模...转载 2019-03-09 22:28:24 · 109 阅读 · 0 评论 -
java并发编程(三)-线程的协作式
怎么样才能让Java里的线程安全停止工作呢?一般来说:程序执行完或者抛出异常。怎么用代码的方式将线程停止呢?可以看到 stop(),resume(),suspend()已不建议使用,stop()会导致线程不会正确释放资源,suspend()容易导致死锁。java线程是协作式,而非抢占式调用线程的interrupt() 方法中断一个线程,并不是强行关闭这个线程,只是跟这...原创 2019-04-09 17:20:15 · 288 阅读 · 0 评论 -
java并发编程(二)-多线程实现的几种方式
一般人说到java多线程方式只有三种,继承Thread类、实现Runnable接口、实现Callable接口通过FutureTask包装器来创建Thread线程方式,在这里补充一种使用ExecutorService、Callable、Future实现有返回结果的多线程的方式。其中前两种方式线程执行完后都没有返回值,后两种是带返回值的。1、继承Thread类创建线程Thread类本质上是实...原创 2019-03-17 17:51:37 · 794 阅读 · 0 评论 -
java并发编程(一)-线程相关的基本概念
CPU核心数和线程数的关系核心数:线程数 = 1:1intel引入超线程技术之后--》 核心数:线程数 = 1:2CPU时间片轮转机制-又称RR 调度时间片轮转法(Round-Robin,RR)主要用于分时系统中的进程调度。为了实现轮转调度,系统把所有就绪进程按先入先出的原则排成一个队列。新来的进程加到就绪队列末尾。每当执行进程调度时,进程调度程序总是选出就绪队列的队首进程,让它...原创 2019-04-07 13:02:38 · 128 阅读 · 0 评论