java线程4对基础方法浅析

本文主要将要对比总结以下4对方法之间的区别和联系:

1.start与run;

2.sleep与wait;

3.join与yiel;

4.suspend与stop.

start和run

start

首先举个例子:

 如上线程执行start()方法后可以正常打出"it's a Thread"日志,再看看start()方法的底层实现:

Thread类implements自Runnable接口,我们再看下Runnable接口,可以发现run()方法是一个抽象方法,我们上面覆盖的方法其实就是这个run()方法:

 这里有一个最关键的native方法start0(),这个方法源码虽然我们看不到,但是通过官方文档得知,jvm是通过这个方法调用Runnable的run()方法的。

执行start方法是有synchronzed锁加持的,所以是线程安全的,同时通过以上代码可以得出start()方法其实是通过调用了start0()这个本地方法,而start0()这个方法里面又调用了Runnable.run()。

用start()方法来启动线程,真正实现了多线程运行,这时无需等待run()方法体中的代码执行完毕而直接继续执行后续的代码。通过调用Thread类的 start()方法来启动一个线程,这时此线程处于就绪(可运行)状态,并没有运行,一旦得到cpu时间片,就开始执行run()方法,这里的run()方法 称为线程体,它包含了要执行的这个线程的内容,Run方法运行结束,此线程随即终止。特别的,当线程已经结束执行后,不能再重新启动,否则会抛出IllegalThreadStateException.

run

run()方法只是类的一个普通方法而已,如果直接调用Run方法,程序中依然只有主线程这一个线程,其程序执行路径还是只有一条,还是要顺序执行,还是要等待run方法体执行完毕后才可继续执行下面的代码,这样就没有达到写线程的目的。

sleep和wait

sleep

sleep方法位于Thread类中,是一个静态本地方法类,可以直接使用类名进行调用,可以让线程等待若干时间。

wait

 

 

 

 wait方法位于Object父类中,意味着所有的对象都能够使用它,功能也是让线程等待若干时间,除了wait方法,Object还提供了notify和notifyAll这两个通知方法来唤醒等待的线程,需要和wait方法配合使用。wait和notify必须在同步(synchronzied)的情况下才能使用,线程的唤醒是不公平的,如果要同时唤醒所有线程可以使用notifyAll();

Object.wait()和Thread.sleep()方法都可以让线程等待若干时间。除了wait()可以被唤醒以外,另一个重要的区别是wait()方法会释放目标对象的锁,而sleep不能。

join和yield

join

join是等待线程结束,很多时候一个线程的输入往往是另一个或者多个线程的输出,此时这个线程就需要等待依赖线程执行完毕,才能继续执行,jdk提供了join方法来实现这个功能。

yield

 
yield意为谦让,yield会让当前线程让出cpu,但是此线程还是会进行cpu资源的争夺,但是能否再次被分配到就不一定了,如果一个线程的作用不重要,或者优先级非常低,而且会占用很多的cpu资源,那么可以适时调用yield,给予其它重要线程更多机会。

suspend和stop

suspend

 

suspend的意思是挂起,意思是让正在运行的线程切换为挂起状态,通过resume进行继续执行.

stop

stop的意思是强行停止,在单线程环境下线程的Thread.stop()方法不会引起数据的不一致,但是在多线程中Thread.stop()这种强行停止正在运行的进程的方法可能带来数据的不一致,严重破坏数据的准确性.
Thread.stop()方法在结束线程时,会直接终止线程,并且释放用来维持对象一致性的锁,如果此时写线程写入数据正写到一半,并强行终止,那么数据就会被写坏。不要顺便使用stop()方法来停止一个线程,这种方法产生的数据不一致性很难察觉出来,也不会有堆栈等错误信息提示,所以在多线程环境下一定要禁止使用stop()方法 。
posted @ 2023-03-14 16:06  HexThinking  阅读(21)  评论(0编辑  收藏  举报