前言



线程,英文Thread。在java中,创建线程的方式有三种:

1、Thread

2、Runnable

3、Callable

在详细介绍下这几种方式之前,我们先来看下Thread类和Runnable接口。

Runnable接口

接口中只有一个run()方法,等待实现类去实现。

package java.lang;
@FunctionalInterface
public interface Runnable { public abstract void run();
}

Thread类

该类实现了Runnable接口,也提供了很多其他的方法,如yield(),join()等

package java.lang;
public
class Thread implements Runnable {
//获取当前线程
public static native Thread currentThread();
public static native void yield();
//一系列的构造函数
public Thread(Runnable target, String name) {
init(null, target, name, 0);
}
public Thread(ThreadGroup group, String name) {
init(group, null, name, 0);
}
/*调用该方法时,jvm会调用run方法
*Causes this thread to begin execution; the Java Virtual Machine
* calls the run method of this thread.
*/
public synchronized void start() { if (threadStatus != 0)
throw new IllegalThreadStateException(); group.add(this); boolean started = false;
try {
start0();
started = true;
} finally {
try {
if (!started) {
group.threadStartFailed(this);
}
} catch (Throwable ignore) { }
}
} }

一、实现Runnable接口

public class i_Runnable {

	/**
* 主线程main方法
* @param args
*/
public static void main(String[] args) {
for (int i = 0; i < 100; i++) {
System.out.println(Thread.currentThread().getName() + "====" + i);
if (i == 20) {
RunnableThreadTest rtt = new RunnableThreadTest();
//子线程
new Thread(rtt, "new Thread[1]====").start();
//new Thread(rtt, "新线程2").start();
}
} }
/**
* RunnableThreadTest实现Runnable接口
* @author YANG
*
*/
static class RunnableThreadTest implements Runnable {
private int i; @Override
public void run() {
for (i = 0; i < 100; i++) {
System.out.println(Thread.currentThread().getName() + " " + i);
} } }
}

执行结果:

注意:

** 执行结果只截取了部分内容。

** 如果RunnableThreadTest类前不加static,会报错No enclosing instance of type i_Runnable is accessible. Must qualify the allocation with
an enclosin。因为只有内部类修饰为静态时,才可以在静态类方法(main方法)中调用该类的成员变量和方法。

二、继承Thread类

public class a_Thread {
public static void main(String[] args) {
Runner1 r=new Runner1();
r.start(); //已经有thread 不需要new,直接调用start即可。 for (int i = 0; i < 100; i++) {
System.out.println("main Thread:"+i);
}
} //Runner1继承Thread类,重写run方法
static class Runner1 extends Thread{
@Override
public void run() { for (int i = 0; i < 100; i++) {
System.out.println("Runner1:"+i);
} } }
}

思考:能不能将上面的r.start(); 改为 r.run();

分析:换成run()方法之后,就变成了普通的方法调用,只有一个主线程,没有子线程。

执行结果:为了方便显示,我们将循环次数改为10。

Runner1:0
Runner1:1
Runner1:2
Runner1:3
Runner1:4
Runner1:5
Runner1:6
Runner1:7
Runner1:8
Runner1:9
main Thread:0
main Thread:1
main Thread:2
main Thread:3
main Thread:4
main Thread:5
main Thread:6
main Thread:7
main Thread:8
main Thread:9

三、实现Callable接口

前面两种方式是传统的线程技术中的内容,第三种方式Callable和Future是jdk1.5之后新增的。我们先来补充点东西,看看这种方式与之前的方式有什么联系。

//实现Callable接口
public class j_CallableTest implements Callable<String> {
public static void main(String[] args) {
j_CallableTest test=new j_CallableTest();
FutureTask<String> ft=new FutureTask<>(test); for (int i = 0; i < 100; i++) {
System.out.println(Thread.currentThread().getName()+" i的值为="+i);
if(i==20){
new Thread(ft,"子线程").start();
}
}
} //重写call方法
@Override
public String call() throws Exception {
int i = 0;
String reString = "";
for (; i < 100; i++) {
reString = Thread.currentThread().getName() + " " + i;
System.out.println(reString);
}
return reString;
}
}

从上面可以看到,new Thread的方式还是用的public Thread(Runnable target, String name); 说明FutureTask也是Runnable类型的,他们之间的关系可以从下图中看出来。

那么,使用Callable和Future的方式有什么特点呢?

我们从他们的定义来看,Callable接口中只有一个方法,返回值为V。前两种方式都是返回void。

@FunctionalInterface
public interface Callable<V> {
/**
* Computes a result, or throws an exception if unable to do so.
*
* @return computed result
* @throws Exception if unable to compute a result
*/
V call() throws Exception;
}

小结:

1、接口实现更灵活,java不支持多继承。在这方面,Runnable和Callable更有优势。

2、返回值问题。Runnable和Thread都不能有返回值,但Callable可以,而且支持多种类型的数据。

就这两点来看,新增的Callable和Future的实现方式优势十分明显啊。但是追到原理,其实这三种都可以归结为一种方式。

java线程(1)——三种创建线程的方式的更多相关文章

  1. 【Java 线程的深入研究1】Java 提供了三种创建线程的方法

    Java 提供了三种创建线程的方法: 通过实现 Runnable 接口: 通过继承 Thread 类本身: 通过 Callable 和 Future 创建线程. 1.通过实现 Runnable 接口来 ...

  2. JavaScript DOM三种创建元素的方式

    三种创建元素的方式: document.write() element.innerHTML document.createElement() 初始HTML内容: <button>btn&l ...

  3. java线程——三种创建线程的方式

    前言 线程,英文Thread.在java中,创建线程的方式有三种: 1.Thread 2.Runnable 3.Callable 在详细介绍下这几种方式之前,我们先来看下Thread类和Runnabl ...

  4. JAVA并发编程学习笔记------线程的三种创建方式

    创建线程一般有如下几个方式: 1. 通过继承Thread类来创建一个线程: /** * 步骤1:定义一个继承Thread类的子类 * 步骤2:构造子类的一个对象 * 步骤3:启动线程: * */ pu ...

  5. Java 数组的三种创建方法,数组拷贝方法

    public static void main(String[] args) {//创建数组的第一种方法int[] arr=new int[6];int intValue=arr[5];//Syste ...

  6. Java 数组的三种创建方法

    public static void main(String[] args) { //创建数组的第一种方法 int[] arr=new int[6]; int intValue=arr[5]; //S ...

  7. 创建线程的三种方式_Callable和Runnable的区别

    Java 提供了三种创建线程的方法 通过实现Runnable接口 通过继承Thread接口 通过Callable和Future创建线程 通过实现 Runnable 接口来创建线程 public cla ...

  8. Java中创建线程的三种方式以及区别

    在java中如果要创建线程的话,一般有3种方法: 继承Thread类: 实现Runnable接口: 使用Callable和Future创建线程. 1. 继承Thread类 继承Thread类的话,必须 ...

  9. Java中创建线程的三种方法以及区别

    Java使用Thread类代表线程,所有的线程对象都必须是Thread类或其子类的实例.Java可以用三种方式来创建线程,如下所示: 1)继承Thread类创建线程 2)实现Runnable接口创建线 ...

随机推荐

  1. iOS之UIKeyboardType 11种键盘图片展示

    UIKeyboardTypeDefault      UIKeyboardTypeASCIICapable  ==  UIKeyboardTypeAlphabet      UIKeyboardTyp ...

  2. [ZJOI2006]超级麻将(动规)

    题目描述 很多人都知道玩麻将,当然也有人不知道,呵呵,不要紧,我在这里简要地介绍一下麻将规则: 普通麻将有砣.索.万三种类型的牌,每种牌有1~9个数字,其中相同的牌每个有四张,例如1砣~9砣,1索~9 ...

  3. [HNOI2003]操作系统(优先队列,堆排序)

    题目描述 写一个程序来模拟操作系统的进程调度.假设该系统只有一个CPU,每一个进程的到达时间,执行时间和运行优先级都是已知的.其中运行优先级用自然数表示,数字越大,则优先级越高. 如果一个进程到达的时 ...

  4. 重装系统后激活win10和office2016

    激活win10: 重装的版本和电脑刚买来是的系统一样的话直接联网,过一段时间就会自动激活.如果不一样可以下载Kms工具激活. 激活office2016: 在开始菜单里双击“我的Office”,登录账号 ...

  5. 01javascript基础

    1.JavaScript:直接写入 HTML 输出流 实例:(只能在 HTML 输出中使用 document.write.如果在文档加载后使用该方法,会覆盖整个文档) <!DOCTYPE htm ...

  6. jquery和vue分别对input输入框手机号码格式化(344)

    jQuery function fomatterTel(val, old) {//val: 当前input的值,old: input上次的值 var str = ""; var t ...

  7. I两种冒泡算法

    两种冒泡算法: 第一个循环,I 定位当前坐标,第二个循环 把 I 之后的每个数都与 I 比较(比 I 小的都去坐标I),第二个循环之后 坐标 I 为数组里最小的数值. 效率比较高的冒泡算法: stat ...

  8. redis学习资料汇总

    redis学习资料汇总 2017年01月07日 22:10:37 阅读数:281 转载:http://blog.csdn.net/wtyvhreal/article/details/50427627 ...

  9. 4,由spring展开的串烧

    一.什么是Spring框架?Spring框架有哪些主要模块? Spring框架是一个为Java应用程序的开发提供了综合.广泛的基础性支持的Java平台.Spring帮助开发者解决了开发中基础性的问题, ...

  10. [网站公告]18:07-18:20阿里云SLB故障造成网站不能正常访问

    (注:由于阿里云SLB管理控制台监控数据不准,实际故障时间是18:07-18:20.) 17:55-18:2018:07-18:20,我们使用的阿里云SLB(负载均衡)中有3台出现突发故障,造成全站无 ...