Java读书笔记(4)-多线程(二)
2016-1-2
线程通信
传统的线程通信
Object类提供了wait(),notify()和notifyAll三个方法
适用情况:synchronized修饰的同步方法或者synchronized方法
wait():导致当前线程等待,直到其他线程调用该同步监视器的notify()或notifyAll方法来唤醒该线程,调用wait方法后本线程会释放对同步监视器的锁定
notify():唤醒在此同步监视器上等待的单个线程。如果有多个线程在等待,则随机唤醒其中一个
notifyAll():唤醒在此同步监视器上等待的所有线程
使用Condition控制线程通信
适用于使用Lock对象来同步的场景,Condition实例被绑定在一个Lock对象
Lock替代了同步方法或同步代码块,Condition替代了同步监视器的功能
await(),signal(),signalAll()
private final Lock lock=new ReentrantLock();
private final Condition cond=lock.newCondition();
cond.await()
cond.signalAll()
使用阻塞队列(BlockingQueue)控制线程通信
add(E e), off(E e), put(E e)
remove(), poll(), take()
element(), peek()
ArrayBlockinQueue, LinkedBlockingQueue, PriorityBlockingQueue, SynchronousQueue, DelayQueue
BlockingQueue<Stirng> bq=new ArrayBlockingQueue<>(2);
bg.put(“Java”)
线程组(ThreadGroup)和未处理的异常
程序可以直接以组为单位控制线程
线程运行途中不能更改所属线程组
ThreadGroup:activeCount(), interrupt(), isDaemon(), setDaemon(), setMaxPriority()
ThreadGroup内还定义了一个很有用的方法:void uncaughtException(Thread t,Throwable e), 可以处理线程组内任意线程所抛出的异常
使用catch捕获异常时,异常不会传播给上一级调用者;但是使用异常处理器对异常进行处理后,异常依然会传播给上一级调用者
线程池
当程序中需要创建大量生存期很短暂的线程时,应该考虑使用线程池。线程池在系统启动时即创建大量空闲的线程
Java5实现的线程池
返回一个ExecutorService对象,该对象代表一个线程池:newCachedThreadPool()newFixedThreadPool(int nThreads),newSingleThreadExecutor()
new ScheduledThreadPool(int corePoolSize),new SingleThreadScheduledExecutor()
使用线程池来执行线程任务的步骤:
调用Executors类的静态工厂方法来创建一个ExecutorService对象,该对象代表一个线程池;
创建Runnable实现类或Callable实现类的实例,作为线程执行任务;
调用ExecutorService对象的submit()方法来提交Runnable实例或者Callable实例;
任务执行完毕,最后关闭线程池shutdown()。
Java7新增的ForkJoinPool
充分利用多CPU,多核CPU的性能优势
将一个任务拆分成多个“小任务”并行计算,再把多个小任务的结果合并成总的计算结果
ForkJoinPool是ExecutorService的实现类,因此是一种特殊的线程池
创建了ForkJoinPool实例之后,就可以调用ForkJoinPool的submit(ForkJoinTask task)或者invoke(ForkJoinTask task)方法来执行指定任务了。其中ForkJoinTask代表一个可以并行,合并的任务。ForkJoinTask是一个抽象类,它还有两个抽象子类:RecursiveAction和RecursiveTask。其中RecursiveTask代表有返回值的任务,而RecursiveAction代表没有返回值的任务。
线程相关类
ThreadLocal类
代表一个线程局部变量,通过把数据放在ThreadLocal中就可以让每个线程创建一个该变量的副本
在编写多线程代码时,可以把不安全的整个变量封装进ThreadLocal,或者把对象与线程相关的状态使用ThreadLocal保存
ThreadLocal类与线程同步机制面向的问题领域是不同的
如果多个资源之间需要共享资源,以实现线程通信,则使用同步机制;如果仅仅只是隔离多个线程之间的冲突,则使用ThreadLocal
包装线程不安全的集合
可以使用Collections提供的静态方法把这些集合包装成线程安全的集合。
<T> Collection<T> synchronizedCollections(Collection<T> c):返回指定collection对应的线程安全的collection;
static <T> List<T> synchronizedList(List<T> list)
static <K,V> Map<K,V> synchronizedMap(Map<K,V> m)
static <T> Set<T> synchronizedSet(Set<T> s)
static <K,V> SortedMap<K,V> synchronizedSortedMap(SortedMap<K,V> m)
static <T> SortedSet<T> synchronizedSortedSet(SortedSet<T> s)
如果需要把某个集合包装成线程安全的集合,则应该在创建之后立即包装
HashMap m=Collections.synchronizedMap(new HashMap());
线程安全的集合类
java.util.concurrent包
支持高效并发访问的集合接口和实现类
以Concurrent开头的集合类:支持并发访问的集合
以CopyOnWrite开头的集合类:适合读取操作远远大于写入操作的场景,如缓存等
转载于:https://www.cnblogs.com/hust_wsh/p/5095858.html
Java读书笔记(4)-多线程(二)相关推荐
- Effective Java读书笔记(二)
Effective Java 读书笔记 (二) 创建和销毁对象 遇到多个构造器参数时要考虑使用构建器 创建和销毁对象 何时以及如何创建对象? 何时以及如何避免创建对象? 如何确保它们能够适时地销毁? ...
- Java读书笔记(8)-单例模式
Java读书笔记(8)-单例模式 今天在阅读<Effective Java 2>第3条时,获知一种使用枚举enum实现单例模式的新方法,然而书上并没有就此展开深入说明,于是上网查阅了一些资 ...
- head first java读书笔记
head first java读书笔记 1. 基本信息 页数:689 阅读起止日期:20170104-20170215 2. 标签 Java入门 3. 价值 8分 4. 主题 使用面向对象的思路介绍J ...
- 《深入浅出DPDK》读书笔记(十二):DPDK虚拟化技术篇(半虚拟化Virtio)
Table of Contents 半虚拟化Virtio 132.Virtio使用场景 133.Virtio规范和原理 11.2.1 设备的配置 1. 设备的初始化 2. 设备的发现 3. 传统模式v ...
- think in java 读书笔记 2 —— 套接字
目录 think in java 读书笔记 1 --移位 think in java 读书笔记 2 -- 套接字 think in java 读书笔记 3 -- 数据报 概要 1. 套接字基本知识 2 ...
- Effective Java 读书笔记(七):通用程序设计
Effective Java 读书笔记七通用程序设计 将局部变量的作用域最小化 for-each 循环优于传统的 for 循环 了解和使用类库 如果需要精确的答案请避免使用 float 和 doubl ...
- #java读书笔记#面向对象2
上一篇java读书系列笔记文章:#java读书笔记#面向对象1 14.Math类的使用(重点) (1)数学操作类:该类没有构造函数,方法均为静态的 (2)掌握内容 A:成员变量 **E:比任何其他值都 ...
- Effective Java读书笔记完结啦
Effective Java是一本经典的书, 很实用的Java进阶读物, 提供了各个方面的best practices. 最近终于做完了Effective Java的读书笔记, 发布出来与大家共享. ...
- Java学习笔记5-1——多线程
目录 前言 核心概念 线程创建 继承Thread类 实现Runnable接口 上述两个方法小结 实现Callable接口 并发问题简介 静态代理模式 线程状态 线程停止(stop) 线程休眠(slee ...
最新文章
- Flash Builder 4 安装ANT插件
- 在Windows Server 2012 R2中搭建SQL Server 2012故障转移集群
- python基础学习[python编程从入门到实践读书笔记(连载四)]:数据可视化项目第15章
- 一个简单的dotnet tool
- python学习笔记(十 三)、网络编程
- 深度学习笔记(16) 误差分析(一)
- Spring Cloud 个人心得 理论
- java中redis存储map集合_使用RedisTemplate存储Map集合的一点注意
- LinkedHashMap内部实现
- PackageManager.getPackageSizeInfo||UserHandle.myUserId()
- C语言关键字浅析-char
- 单片机控制IIC协议EEPROM芯片24C512之模块化编程(持续更新中)
- Unity的虚拟摇杆
- 2019-2020年数学建模竞赛心得体会
- echarts的x轴y轴的颜色改变
- python distribute包管理工具安装AttributeError错误
- Windows bat脚本获取administrator权限
- 2022年高新技术企业认定的补贴有多少?
- 当程序员后,才突然明白的21件事……
- Linux小实验11|添加组group,添加用户aa、bb并加入group组 (2)新建文件/abc.txt (3)设置用户aa对文件拥有读、写和执行权限
热门文章
- 【Qt】Qt中QJsonValue类
- 【Linux】一步一步学Linux——unzip命令(68)
- 【Linux系统编程】进程的控制:结束进程、等待进程结束
- 【Android】dip、dp、sp、pt和px的区别
- python list删除元素_python中List添加、删除元素的几种方法
- 电脑桌面便签_电脑桌面定时提醒记事本便签软件
- 管理员密码的php文件,ecshop网站后台管理员密码找回办法
- 微信小程序 事件点击后如何动态增删class类名(自用,没毛病)
- 记录docker开发hadoop,解决bug Datanode denied communication with namenode because hostname cannot be
- 路径总和 III—leetcode437