【Java】什么是线程?Thread和Runnable区别
1.1 多线程原理
昨天的时候我们已经写过一版多线程的代码,很多同学对原理不是很清楚,那么我们今天先画个多线程执行时序图
来体现一下多线程程序的执行流程。
代码如下:
自定义线程类:

测试类:

流程图:
程序启动运行
main
时候,
java
虚拟机启动一个进程,主线程
main
在
main()
调用时候被创建。随着调用
mt
的对象的
start
方法,另外一个新的线程也启动了,这样,整个应用就在多线程下运行。
通过这张图我们可以很清晰的看到多线程的执行流程,那么为什么可以完成并发执行呢?我们再来讲一讲原理。
多线程执行时,到底在内存中是如何运行的呢?以上个程序为例,进行图解说明:
多线程执行时,在栈内存中,其实
每一个执行线程都有一片自己所属的栈内存空间
。进行方法的压栈和弹栈
当执行线程的任务结束了,线程自动在栈内存中释放了。但是当所有的执行线程都结束了,那么进程就结束了
1.2 Thread类
在上一天内容中我们已经可以完成最基本的线程开启,那么在我们完成操作过程中用到了
java.lang.Thread
类,
API
中该类中定义了有关线程的一些方法,具体如下:
构造方法:
public Thread()
:
分配一个新的线程对象。
public Thread(String name)
:
分配一个指定名字的新的线程对象。
public Thread(Runnable target)
:
分配一个带有指定目标新的线程对象。
public Thread(Runnable target,String name)
:
分配一个带有指定目标新的线程对象并指定名字。
常用方法:
public String getName()
:
获取当前线程名称。
public void start()
:
导致此线程开始执行
; Java
虚拟机调用此线程的
run
方法。
public void run()
:
此线程要执行的任务在此处定义代码。
public static void sleep(long millis)
:
使当前正在执行的线程以指定的毫秒数暂停(暂时停止执行)。
public static Thread currentThread()
:
返回对当前正在执行的线程对象的引用。
翻阅
API
后得知创建线程的方式总共有两种,一种是继承
Thread
类方式,一种是实现
Runnable
接口方式,方式一我
们上一天已经完成,接下来讲解方式二实现的方式。
1.3 创建线程方式二
采用
java.lang.Runnable
也是非常常见的一种,我们只需要重写
run
方法即可。
步骤如下:
1.
定义
Runnable
接口的实现类,并重写该接口的
run()
方法,该
run()
方法的方法体同样是该线程的线程执行体。
2.
创建
Runnable
实现类的实例,并以此实例作为
Thread
的
target
来创建
Thread
对象,该
Thread
对象才是真正
的线程对象。
3.
调用线程对象的
start()
方法来启动线程。
代码如下:

通过实现
Runnable
接口,使得该类有了多线程类的特征。
run()
方法是多线程程序的一个执行目标。所有的多线程
代码都在
run
方法里面。
Thread
类实际上也是实现了
Runnable
接口的类。
在启动的多线程的时候,需要先通过
Thread
类的构造方法
Thread(Runnable target)
构造出对象,然后调用
Thread
对象的
start()
方法来运行多线程代码。
实际上所有的多线程代码都是通过运行
Thread
的
start()
方法来运行的。因此,不管是继承
Thread
类还是实现
Runnable
接口来实现多线程,最终还是通过
Thread
的对象的
API
来控制线程的,熟悉
Thread
类的
API
是进行多线程
编程的基础。
tips:Runnable
对象仅仅作为
Thread
对象的
target
,
Runnable
实现类里包含的
run()
方法仅作为线程执行体。
而实际的线程对象依然是
Thread
实例,只是该
Thread
线程负责执行其
target
的
run()
方法。
1.4 Thread和Runnable的区别
如果一个类继承
Thread
,则不适合资源共享。但是如果实现了
Runable
接口的话,则很容易的实现资源共享。
总结:
实现
Runnable
接口比继承
Thread
类所具有的优势:
1.
适合多个相同的程序代码的线程去共享同一个资源。
2.
可以避免
java
中的单继承的局限性。
3.
增加程序的健壮性,实现解耦操作,代码可以被多个线程共享,代码和线程独立。
4.
线程池只能放入实现
Runable
或
Callable
类线程,不能直接放入继承
Thread
的类。
扩充:在
java
中,每次程序运行至少启动
2
个线程。一个是
main
线程,一个是垃圾收集线程。因为每当使用
java
命令执行一个类的时候,实际上都会启动一个
JVM
,每一个
JVM
其实在就是在操作系统中启动了一个进
程。
1.5 匿名内部类方式实现线程的创建
使用线程的内匿名内部类方式,可以方便的实现每个线程执行不同的线程任务操作。
使用匿名内部类的方式实现
Runnable
接口,重新
Runnable
接口中的run方法:

浙公网安备 33010602011771号