
JUC并发编程
文章平均质量分 90
new一个对象_
天还没亮人们就开始赶路
展开
-
JUC并发编程设计模式
有如下场景,做一个系统的健康状态监控(记录电脑CPU的使用率、内存的使用率)实现定时监控。实现这样一个场景,可用一个后台的监控线程不断记录。—— stop()方法会真正杀死线程,如果这时线程锁住了共享资源,那么当它被杀死后就再也没有机会释放锁,其它线程将永远无法获取锁。但却有着很大的区别,线程1输出a 5次,线程2输出b 5次,线程3输出c 5次。:监控线程每隔1s监控系统,主线程处于休眠状态,3.5秒后休眠状态被打断。比如,先打印2后打印1(如果不加控制两个线程被CPU调度的时间不受控制)原创 2023-03-09 13:27:26 · 731 阅读 · 0 评论 -
ReentranLock(可重入锁)
条件变量synchronized 中也有条件变量,就是我们讲原理时那个 waitSet 休息室,当条件不满足时进入 waitSet 等待ReentrantLock 的条件变量比 synchronized 强大之处在于,它是支持多个条件变量的,这就好比● synchronized 是那些不满足条件的线程都在一间休息室等消息● 而 ReentrantLock 支持多间休息室,有专门等烟的休息室、专门等早餐的休息室、唤醒时也是按休息室来唤醒使用要点:● await 前需要获得锁。原创 2023-03-08 10:47:00 · 1130 阅读 · 0 评论 -
JUC并发编程——多把锁
线程1按AB的顺序加锁,先获得锁A,线程2也是按AB的顺序进行加锁,线程2此时想获取对象A的锁时获取失败(进入对象A的EntryList中阻塞),这时线程1再尝试获取B对象的锁。死锁是两个线程持有对方需要的锁,导致线程都无法继续向下运行,两个线程均陷入阻塞;● 使两个线程的执行时间有一定的交错(不集中在一起执行/设置睡眠的时间为一个随机数===>将其指令交错开,第一个线程很快运行完,第二个线程将没有机会改变对方的结束条件)现在小南要学习,小女要睡觉,但如果只用一间屋子(一个对象锁)的话,那么并发度很低。原创 2023-03-07 16:03:55 · 645 阅读 · 0 评论 -
JUC并发编程——Park & Unpark
● 调用 LockSupport.unpark(目标线程) 或调用了线程 的 interrupt() ,或是等待超时,会让目标线程从TIMED_WAITING–> RUNNABLE。● 当前线程等待时间超过了 n 毫秒,或t 线程运行结束,或调用了当前线程的 interrupt() 时,当前线程从TIMED_WAITING --> RUNNABLE。● t 线程等待时间超过了 n 毫秒,或调用 obj.notify() , obj.notifyAll() , t.interrupt() 时。原创 2023-03-07 10:47:18 · 552 阅读 · 0 评论 -
JUC并发编程——wait-notify
●obj.wait()让进入 object 监视器的线程到 waitSet 等待●在 object 上正在 waitSet 等待的线程中挑一个唤醒●让 object 上正在 waitSet 等待的线程全部唤醒它们都是线程之间进行协作的手段,都属于 Object 对象的方法。无论是wait还是notify必须获得此对象的锁,才能调用这几个方法示例try {/* 需先获取对象锁,成为Owner后才能调wait();原创 2023-03-06 15:27:50 · 561 阅读 · 0 评论 -
synchronized底层
于是,小南干脆在门上刻上了自己的名字:【小南专属房间,其它人勿用】,下次来用房间时,只要名字还在,那么说明没人打扰,还是可以安全地使用房间。),但他们的书包样式都一样,因此每次进门前得翻翻书包,看课本是谁的,如果是自己的,那么就可以进门,这样省的上锁解锁了。如果在尝试加轻量级锁的过程中,CAS操作无法成功,这时一种情况就是有其他线程为此对象加上了轻量级锁(有竞争),这时需要进行锁膨胀,将轻量级锁变为重量级锁。小女是要用房间,但使用的时间上是错开的,小南白天用,小女晚上用。原创 2023-03-05 15:34:52 · 671 阅读 · 0 评论 -
Java线程安全习题
多线程环境下进行测试某个类的线程安全,安全问题不容易复现,上述测试中使用sleep()增加其时间间隔的方式期望线程上下文切换的机率增大,使现象更容易出现。为节省时间我们还可以使用编写测试脚本的方式(一旦出现线程安全问题,会在某次循环中将其展示出来)。共享变量,其只能保护自身,并不能影响到另一个对象上的getMoney() 、setMoney()。锁加在两个对象上相当于两个线程进入了两个房间,起不到保护线程作用。若要分析线程安全问题,需考虑哪部分代码属于临界区(找出临界区便可对其加锁)原创 2023-02-28 23:49:44 · 976 阅读 · 0 评论 -
线程安全实例分析
线程1、2均执行方法内的代码,线程1执行get(“key”) == null,还未执行完,线程发生上下文切换轮到线程2执行,线程2也执行到此处得到的get(“key”) == null,线程2发现为null后put(“key”, v2),完成后又切换为线程1,线程1又put(“key”, v1)。② Connection也是线程安全的,Connection属于方法内的局部变量,即使有多个线程访问,线程1创建的为Connection1而线程2创建的为Connection2,两者独立互不干扰。原创 2023-02-28 15:11:31 · 566 阅读 · 0 评论 -
JUC并发编程——线程安全问题
本次使用阻塞式的解决方案:synchronized,来解决上述问题,即俗称的【对象锁】,它采用互斥的方式让同一时刻至多只有一个线程能持有【对象锁】,其它线程再想获取这个【对象锁】时就会阻塞住。这中间即使 t1 的 cpu 时间片不幸用完,被踢出了门外(不要错误理解为锁住了对象就能一直执行下去哦),这时门还是锁住的,t1 仍拿着钥匙,t2 线程还在阻塞状态进不来,只有下次轮到 t1 自己再次获得时间片时才能开门进入。:2 1s 后 1【调用a()时锁住的为类对象,调用b()时锁住的为n1对象】原创 2023-02-27 14:35:19 · 350 阅读 · 0 评论 -
JUC并发编程(二)
当调用了 start() 方法之后,注意,Java API 层面的 RUNNABLE 状态涵盖了 操作系统 层面的【可运行状态】、【运行状态】和【阻塞状态】(由于 BIO 导致的线程阻塞,在 Java 里无法区分,仍然认为是可运行)有一种特殊的线程叫做守护线程,只要其它非守护线程运行结束了,即使守护线程的代码没有执行完,也会强制结束。—— 如果调用了阻塞 API,如 BIO 读写文件,这时该线程实际不会用到 CPU(调度器不会考虑调度阻塞状态的线程),会导致线程上下文切换,进入【阻塞状态】原创 2023-02-26 17:47:09 · 399 阅读 · 0 评论 -
Java线程——常见方法
①:直接调用run方法并不会启动新的线程} };t1 . run();} }} };t1 . run();} }} };t1 . run();} }} };t1 . run();} }} };t1 . run();} }} };t1 . run();} }} };t1 . run();} }} };t1 . run();} }原创 2023-02-23 11:12:43 · 988 阅读 · 0 评论 -
Java线程
两个线程同时运行均要使用CPU,While(ture)为死循环,两个线程均需要不断使用CPU,而两个线程大量使用CPU会造成CPU占用率达到100%,其他代码、操作系统其他程序就会暂停卡住。因为以下一些原因导致 cpu 不再执行当前的线程,转而执行另一个线程的代码(从使用CPU到不适用CPU称之为线程的一次上下文切换)当然它的底层是否由多个核心对这两个线程并行执行还是一个核心对它们并发处理,包括打印的前后顺序是不由我们控制的。(快照:只能查看某一刻) 查看某个 Java 进程(PID)的所有线程状态。原创 2023-02-22 14:34:47 · 3336 阅读 · 0 评论 -
JUC并发编程——进程与线程
● 但如果是四核 cpu,各个核心分别使用线程 1 执行计算 1,线程 2 执行计算 2,线程 3 执行计算 3,那么 3 个线程是并行的,花费时间只取决于最长的那个线程运行的时间,即 11ms 最后加上汇总时间只会花费 12ms。● 进程就可以视为程序的一个实例。● 有些任务,经过精心设计,将任务拆分,并行执行,当然可以提高程序的运行效率。单核 cpu 下,多线程不能实际提高程序运行效率,只是为了能够在不同的任务之间切换,不同线程轮流使用cpu ,不至于一个线程总占用 cpu,别的线程没法工作。原创 2023-02-21 16:39:21 · 457 阅读 · 0 评论