Java多线程——<二>将任务交给线程,线程声明及启动
一、任务和线程
《thinking in java》中专门有一小节中对线程和任务两个概念进行了具体的区分,这也恰好说明任务和线程是有区别的。
正如前文所提到的,任务只是一段代码,一段要达成你目的的代码,这段代码写在哪,怎么写其实无所谓,只是因为你希望java的多线程机制能够识别并调用你编写的任务,所以规定了Runnable接口,让你的任务来实现该接口,把你想做的工作在实现该接口的run方法中实现。
那么,已经定义了任务类,那任务和线程有什么关系呢?
java的线程是用来驱动任务执行的,也就是说你得把任务挂载到一个线程上,这样该线程才能驱动你定义的任务来执行。
二、定义线程
1.显示的定义线程的过程就是将任务附着到线程的过程。线程Thread自身并不执行任何操作,它只是用来被多线程机制调用,并驱动赋予它的任务。
如前次文章提到的任务类定义如下:
public class Task implements Runnable {
protected int countDown = 10;
private static int taskCount = 0 ;
private final int id = taskCount++;
public Task(){}
public Task(int countDown){
this.countDown = countDown;
}
public String status(){
return "#"+id+"("+(countDown>0?countDown:"Task!")+"). ";
}
@Override
public void run() {
while(countDown-->0){
System.out.print(status());
Thread.yield();
}
}
}
声明线程并将任务附着到该线程上:
Thread t = new Thread(new Task());
这样,任务就附着给了线程,下面就是让线程启动,只需要如下的调用:
t.start();
至此,线程声明ok。
有时,我会想,是不是像任务和线程的概念分离一样,此时只是声明了线程,而java的线程机制并不会调用该线程运行,还需要特殊的调用才能实现多线程执行。但是下面的一段代码告诉我,Thread类的start方法就是触发了java的多线程机制,使得java的多线程能够调用该线程
public static void main(String[] args){
Thread t = new Thread(new Task());
t.start();
System.out.println("Waiting for Task");
}
输出结果如下:
Waiting for Task
#0(9). #0(8). #0(7). #0(6). #0(5). #0(4). #0(3). #0(2). #0(1). #0(Task!).
先输出“Waiting for Task”证明调用完start()方法后,立即返回了主程序,并开始执行下面的语句。而你声明的t线程已经去被java的多线程机制调用,并驱动着它的任务运行了。
2.补充
想看到更多的线程任务运行,可以用下面的这段代码
public static void main(String[] args){
for(int i = 0 ; i < 5 ; i++){
new Thread(new Task()).start();
}
System.out.println("Waiting for Task");
}
输出如下:
Waiting for Task
#0(9). #2(9). #4(9). #0(8). #2(8). #4(8). #0(7). #2(7). #4(7). #0(6). #2(6). #4(6). #0(5). #2(5). #4(5). #0(4). #2(4). #4(4). #3(9). #2(3). #4(3). #2(2). #4(2). #2(1). #4(1). #2(Task!). #4(Task!). #1(9). #0(3). #0(2). #0(1). #0(Task!). #3(8). #1(8). #3(7). #1(7). #3(6). #1(6). #3(5). #3(4). #3(3). #3(2). #3(1). #3(Task!). #1(5). #1(4). #1(3). #1(2). #1(1). #1(Task!).
上面的输出说明不同任务的执行在线程被换进换出时混在了一起——由线程调度器自动控制。不同版本的jdk线程调度方式不同,所以产生的结果也不相同。
这里涉及了垃圾回收器的一个问题,每个Thread都注册了它自己,因此确实有一个对它的引用,而且在它的任务退出其run并死亡之前,垃圾回收器无法清除它。
注:以上代码均来自《thinking in java》,内容大部分是个人理解和总结,如有错误请各位指正
Java多线程——<二>将任务交给线程,线程声明及启动的更多相关文章
- Java多线程(三)如何创建线程
点我跳过黑哥的卑鄙广告行为,进入正文. Java多线程系列更新中~ 正式篇: Java多线程(一) 什么是线程 Java多线程(二)关于多线程的CPU密集型和IO密集型这件事 Java多线程(三)如何 ...
- Java多线程(一) 什么是线程
声明:本系列大多是翻译自https://www.javatpoint.com,加上自己的增删改,尽力写的系统而通俗易懂,后文不再重复声明. 点我跳过黑哥的卑鄙广告行为,进入正文. Java多线程系列更 ...
- “全栈2019”Java多线程第十四章:线程与堆栈详解
难度 初级 学习时间 10分钟 适合人群 零基础 开发语言 Java 开发环境 JDK v11 IntelliJ IDEA v2018.3 文章原文链接 "全栈2019"Java多 ...
- “全栈2019”Java多线程第十章:Thread.State线程状态详解
难度 初级 学习时间 10分钟 适合人群 零基础 开发语言 Java 开发环境 JDK v11 IntelliJ IDEA v2018.3 文章原文链接 "全栈2019"Java多 ...
- “全栈2019”Java多线程第七章:等待线程死亡join()方法详解
难度 初级 学习时间 10分钟 适合人群 零基础 开发语言 Java 开发环境 JDK v11 IntelliJ IDEA v2018.3 文章原文链接 "全栈2019"Java多 ...
- “全栈2019”Java多线程第六章:中断线程interrupt()方法详解
难度 初级 学习时间 10分钟 适合人群 零基础 开发语言 Java 开发环境 JDK v11 IntelliJ IDEA v2018.3 文章原文链接 "全栈2019"Java多 ...
- Java多线程系列--“基础篇”06之 线程让步
概要 本章,会对Thread中的线程让步方法yield()进行介绍.涉及到的内容包括:1. yield()介绍2. yield()示例3. yield() 与 wait()的比较 转载请注明出处:ht ...
- Java多线程系列--“基础篇”07之 线程休眠
概要 本章,会对Thread中sleep()方法进行介绍.涉及到的内容包括:1. sleep()介绍2. sleep()示例3. sleep() 与 wait()的比较 转载请注明出处:http:// ...
- Java多线程系列--“基础篇”10之 线程优先级和守护线程
概要 本章,会对守护线程和线程优先级进行介绍.涉及到的内容包括:1. 线程优先级的介绍2. 线程优先级的示例3. 守护线程的示例 转载请注明出处:http://www.cnblogs.com/skyw ...
随机推荐
- 【SNMP】Linux系统下安装net-snmp
这里使用的snmp的版本是net-snmp-5.7.3下载地址:http://www.net-snmp.org/download.html 安装步骤: 1.解压缩安装包: tar -xzvf net- ...
- javascript之Array基础篇
整理了 Array 中很基础的要掌握的知识点,希望可以帮助初学者,也希望自己以后多用多融会贯通. 创建数组 使用Array构造函数: var a=new Array();//创建一个空数组 var a ...
- 什么是WEB服务器?
简单的理解: 一个公用的服务器,你可以放置网站文件,让全世界浏览,可以放文件,全世界下载.web服务器一般指网站服务器. web服务器是基于网站架设的服务器,我们平时可以浏览的网页都是在别人的服务 ...
- JavaScript 内部对象
欢迎访问我的个人博客:http://blog.cdswyda.com/ 原文文地址:JavaScript 内部对象
- Jexus 高并发请求的优化技巧 笔记
Jexus web server 5.1 每个工作进程的最大并发数固定为1万,最多可以同时开启4个工作进程,因此,每台Jexus V5.1服务器最多可以到支持4万个并发连接.但是,按照linux系统的 ...
- java 环境变量设置
JAVA_HOME C:\Program Files\Java\jdk1.7.0 PATH %JAVA_HOME%\bin;%JAVA_HOME%\jre\bin; CLASSPATH .;%JAV ...
- vc列表控件的初始化
void CManageProcessDlg::InitList() { m_ListProcess.SetExtendedStyle(m_ListProcess.GetExtendedStyle( ...
- 重绘panel控件,实现panel的阴影效果
最近想在项目中添加一个要有阴影的panel控件,找了好多资料,最后通过采用图片的方式实现了panel的阴影效果,效果图如下: 重绘代码如下: using System; using System.Co ...
- PyQt4学习笔记1:PyQt4第一个程序
创建一个 PyQt4 一般可以通过很少的步骤完成.通常的方法是用Qt 提供的QtDesigner工具创建界面.使用QtDesigner,可以方便地创建复杂的GUI界面.然后,可以在窗口上创建部件, 添 ...
- mysql导入的时候提示“1046-No Database selected”的解决办法
进入phpmyadmin后,先点击左边的要导入的数据库,进入后再点击右上角的“导入‘按钮即可 详细说明 http://www.xmxwl.net/help/member/20160325/13653. ...