多线程总结
来源:互联网 发布:龙信数据怎么样 编辑:程序博客网 时间:2024/06/09 19:38
多线程总结
一、提到多线程,就不得不理解以下几点:
1.程序,进程,线程这三者之间的关系?
三者的逻辑关系是程序调用进程,进程调用线程,一般来说程序下面都是多进程,不同的进程分工不同;进程下面也基本上是多线程的。
可以这样下定义:进程是系统进行资源分配和调用的独立单位,每一个进程,都由它自己的内存空间和系统资源
线程是进程的执行单元,执行路径,线程也是程序使用CPU的最基本单位
2.单线程与多线程以及多线程的意义?
多线程应用范围:主要是大型项目的开发
优点:将大流程,拆分若干个小流程,条理清晰,便于阅读!多线程一般是异步结构的,执行效率高!
如果程序只有一条执行路径,这就是单线程;相反如果程序有多条路径,那么就是多线程
看下面这段程序:
public class Thread {
public static void main(String[]args) {
//code..........
............
...........
}
}
这里面至少存在两条程序,一条是主线程main,另外一条就是垃圾回收线程,即JVM一遍"执行"main,"一边"也在执行垃圾回收机制
所以说Java支持多线程,而多线程的意义它可以让程序在一个时间段执行多个事情,提高了应用程序的使用率;
比如上面那个例子,如果是单线程,那么JVM不得不执行一会main线程然后停下来去执行垃圾回收机制
3.理解并发与并行
思考:我们在一边玩游戏,一边带上耳机听歌,请问玩游戏与听歌是同时进行的吗?
显然不是,因为CPU在某一个时间点上只能做一件事,我们玩游戏,CPU就切换到执行游戏进程,听歌,CPU就切换到听歌进程;CPU就这样反复做这高效率的切换动作,这种切换是随机的,但是让我们人感觉到就是同时发生的,这就是并发的概念
并发:通过CPU调度算法,让用户看上去同时执行,实际上,是通过CPU在高速切换,并不是真正的额同时
并行:多个CPU实例或者多台机器同时执行一段处理逻辑,这就是真正的同时;
二,如何创建线程?
这里先提两个:run()方法,与start()方法,run()方法里面存放着Thread线程对象需要执行的代码;调用start()方法,让所创建的线程处于就绪状态。
创建线程的方式一:
1.类去继承(extends)Thread类
2.该类重写Thread类的run方法,并且将线程要执行的代码,存放到run方法中
3.线程对象调用start方法,开启线程,线程会自动执行run方法
创建线程的方式二:
1.存放线程执行代码的类去实现(implements) Runnable接口
2.重写所实现接口的run方法,并将线程执行代码存放在run方法中
3.创建Thread对象,也就是创建线程
4.Thread线程对象调用start方法,启动线程
总结:
实现Runnable接口比继承Thread类所具有的优势:
1):适合多个相同的程序代码的线程去处理同一个资源
2):可以避免java中的单继承的限制
3):增加程序的健壮性,代码可以被多个线程共享,代码和数据独立。
三、线程在程序中的几种状态
线程调度
线程有5种基本状态:
1、出生:新建状态(Thread t = newThread),当创建线程对象后,就进入了新建状态。
2、就绪:就绪状态(runnable),t.start()被调用;当线程对象被创建后,其他线程调用了该线程的start()方法,该线程就进入了队列,说明此线程做好了准备,随时等待cpu调度执行。
3、获得CPU执行权:运行状态(running)当cpu时间片分给就绪状态的线程时,该线程就真正的执行起来,进入了运行状态。
4、阻塞状态(blocked)阻塞状态是因为线程因为某种原因放弃了cpu的使用权,暂时停止运行,直到线程进入就绪状态,才有机会运行。
阻塞状态分为3种情况:
执行-等待阻塞(t.wait()):运行状态中的线程执行wait()方法,使本线程进入到等待阻塞状态;自己醒不了,只能用notify()或者notifyAll()唤醒,处于等待状态的线程会释放CPU执行权,同时释放锁资源。
同步阻塞 -- 线程在获取synchronized同步锁失败(因为锁被其它线程所占用),它会进入同步阻塞状态;
其他阻塞 -- 通过调用线程的sleep()或join()或发出了I/O请求时,线程会进入到阻塞状态。当sleep()状态超时、join()等待线程终止或者超时、或者I/O处理完毕时,线程重新转入就绪状态。
5、死亡状态(Dead):线程执行完了或者因异常退出了run()方法,该线程结束生命周期。
处于阻塞状态的线程往往存在性能瓶颈,也是我们需要特别关注的。如果是因为竞争同步锁引发的死锁或者的响应时间的延长,需要找到这些处于blocked状态的线程在等待什么资源,通常情况下是数据库连接或者是日志的输出。
四、多线程的安全隐患以及synchronized监视器(锁)
1.多线程并发安全问题
*由于线程之间运行是异步的,互相没有牵制,但如果
*同时访问同一资源时就出现了“抢”的现象。由于线程
*发生切换现象的实际不确定导致代码执行顺序可能未
*按照设计的顺序执行,出现一系列的不可预知后果
public class SyncDemo{
public staticvoid main(String[] args) {
finalTable table = new Table();
Thread t1= new Thread(){
publicvoid run(){
while(true){
intbean = table.getBean();
Thread.yield();//模拟线程发生了切换
System.out.println(
getName()+":"+bean);
}
}
};
Thread t2= new Thread(){
publicvoid run(){
while(true){
intbean = table.getBean();
Thread.yield();//模拟线程发生了切换
System.out.println(getName()+":"+bean);
}
}
};
t1.start();
t2.start();
}
}
class Table{
private intbeans = 20;
/**
* 当一个方法被synchronized修饰后,该方法称为
* 同步方法,即:多个线程不能同时进入到方法内部
* 去执行代码。这样就不会同时对beans这个数据
* 进行操作,没有抢的问题,就不会出现并发安全
* 问题了。
*
* 在一个方法上使用synchronized修饰,那么
* 同步监视器对象就是该方法所属对象,即方法
* 内部看到的this
* @return
*/
publicsynchronized int getBean(){
if(beans==0){
thrownew RuntimeException("没有豆子了!");
}
Thread.yield();//模拟线程发生了切换
returnbeans--;
}
}
2.同步代码块可以解决线程安全问题
三、线程池
JDK1.6中的内置线程池——Executor框架
JDK中提供了一套Executor框架支持更好的控制多线程操作。在concurrent包中是并发线程的核心,其中ThreadPoolExecutor表示一个线程池,Executors扮演者线程池工厂的角色,通过Executors可以创建特定功能的线程池。
- //1、new一个固定线程数量的线程池,有一个新任务提交时,从该线程池中查找是否有空闲线程,如果没有新的任务会被暂存于一个任务队列中,待有空闲线程后再执行。
- ExecutorService threadPoolFix=Executors.newFixedThreadPool(3);//每次3个线程,执行3个任务;其他任务等待。
- //2、缓存线程池--返回一个跟任务数相等的线程数量,有多少任务就产生多少个线程进行处理。动态变化-干完了定期回收
- ExecutorService threadPoolCache=Executors.newCachedThreadPool();
- //3、只有一个线程的线程池,任务按照任务队列顺序FIFO执行,保证线程池始终中有一个线程,当前死了,立马搞一个顶替工作
- ExecutorService threadOne=Executors.newSingleThreadExecutor();
- //4、线程池大小为1,支持在给定时间执行某任务,如在某个固定的延时之后执行,或者周期性执行。-定时器效果
- ExecutorService threadSingleScheduled=Executors.newSingleThreadScheduledExecutor();
- //5、指定一定固定大小的线程池
- ExecutorService threadScheduled=Executors.newScheduledThreadPool(5);
- 多线程总结--多线程介绍
- 多线程_多线程总结
- 多线程总结
- 多线程总结
- 多线程总结
- 多线程总结
- 多线程总结
- 多线程总结
- 多线程总结
- 多线程总结
- 多线程总结:
- 多线程总结
- 多线程总结
- 多线程总结
- 多线程总结
- 多线程总结
- 多线程总结
- 多线程总结
- input子系统
- gcc 如何编译so 和 objdump 反汇编
- CentOS7.x 安装、配置JDK、Maven
- spring:tomcat启动服务报错
- intellij idea14 +svn配置 .
- 多线程总结
- Python求解排列中的逆序数个数
- 教务管理系统雏形
- tips:linux命令积累
- RPM安装 MYSQL
- 对Linux中多线程编程中pthread_join的理解
- PyQt4开发环境搭建指导
- loadrunner Web_类函数之web_check_box()
- WebService