❤️线程常用方法
- object.start()
后处于就绪状态,等待CPU分配时间,执行对应的复写的run()方法 - Thread.sleep()
即线程一返回就绪状态,此时其他线程将竞争到CPU分配的时间 - Thread.yield()
后释放CPU处理时间,给所有人一起竞争 - object.join()
该线程独自全部完成后才把CPU资源释放出来 - object.interrupt()
该线程的join,sleep阻塞被疏通
❤️如何正确停止线程
错误方法一
stop() 是Java中停止线程的方法,但是不正确:
会使线程戛然而成
无法知道完成了什么
不知道哪些工作还没有做
无法进行清理工作
即:
会使线程突然整个停止,没有跟随的一些工作
错误方法二
interrupt
初衷并不是为了停止线程
作用是:
当线程在join(),sleep()阻塞状态下,这些状态能被清除
所以在有interrupt时,join(),sleep(),被try-catch-surronding可以使程序做出相应的反应,而不至于直接强行被停止而不知道发生了什么。
有方法
.interrupt(), 用来调用中断
.isInterrupted(),用来判断是否中断,旗标
正确方法一:利用布尔值作为旗标
volatile boolean keepRunning = true;
while(keepRunning){
….
};
通过修改标识keepRunning来进行处理
在标识为结束后,会单一的完成while()中的步骤,从而提供了善后处理的功能
正确方法二:利用interrupt作为旗标
while(!this.isInterrupt()){
//内部的Thread.sleep()
//不可以用try-catch圈起来,否则将因为捕捉异常而无效
…
}
❤️例子
一
package base;
public class WrongInterrupt extends Thread{
public static void main(String[] args){
WrongInterrupt thread = new WrongInterrupt();
System.out.println("Start thread...");
thread.start();
try {
Thread.sleep(3000);
} catch (InterruptedException e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
System.out.println("Interrupting thread...");
thread.interrupt();
System.out.println("Stopping application...");
}
public void run(){
//第一种情况!*************************************************
while(true){
System.out.println("Thread is running...");
long time = System.currentTimeMillis();//获得当前时间,毫秒
while((System.currentTimeMillis()-time<1000)){
//减少品目输出的空循环
}
}
}
//*************************************************
}
运行结果
public void run(){
//第二种情况!*************************************************
while(!this.isInterrupt()){
//检测到Thread被中断,则会停止
System.out.println("Thread is running...");
long time = System.currentTimeMillis();
while((System.currentTimeMillis()-time<1000)){
//减少品目输出的空循环
}
//*************************************************
}
运行结果
二
package base;
import org.omg.Messaging.SyncScopeHelper;
public class WrongInterrupt extends Thread{
public static void main(String[] args){
WrongInterrupt thread = new WrongInterrupt();
System.out.println("Start thread...");
thread.start();//执行类中的run方法
try {
Thread.sleep(6000); //主方法中的阻塞
} catch (InterruptedException e) { //从而
// TODO Auto-generated catch block //延长
e.printStackTrace(); //到达
} //下面
System.out.println("Interrupting thread..."); //这一条代码的时间
thread.interrupt();//试图疏通run中的阻塞
System.out.println("Stopping application...");
}
public void run(){
while(!this.isInterrupted()){
//object.interrupt()后,疏通了sleep的阻塞,但是仅有这一个中断并没有中断线程,而是中断了阻塞的过程
System.out.println("Thread is running...");
long time = System.currentTimeMillis();
try {
Thread.sleep(1000); //然而没有
} catch (InterruptedException e) { //所以继续运行
// TODO Auto-generated catch block
e.printStackTrace();
}
}
}
}
运行结果
/***********************第二种情况************************/
while(!this.isInterrupted()){
System.out.println("Thread is running...");
Thread.sleep(1000);//没有try-catch包围
//则此处报错,!【该线程】!中止
}
/*********************************************************/
运行结果
三
class Example3 extends Thread {
volatile boolean stop = false; //volatile容易改变的
public static void main( String args[] ) throws Exception {
Example3 thread = new Example3();
System.out.println( "Starting thread..." );
thread.start();
Thread.sleep( 3000 );
System.out.println( "Asking thread to stop..." );
thread.stop = true;//如果线程阻塞,将不会检查此变量 !!重要
thread.interrupt();//解除程序阻塞,用boolean去控制线程的结束
Thread.sleep( 3000 );
System.out.println( "Stopping application..." );
//System.exit( 0 );
}
public void run() {
while ( !stop ) {
System.out.println( "Thread running..." );
try {
Thread.sleep( 1000 ); //程序阻塞
} catch ( InterruptedException e ) {
System.out.println( "Thread interrupted..." );
}
}
System.out.println( "Thread exiting under request..." );
}
}
/**
@brief 既要用sleep()
(而不是用while循环,由布尔变量控制比较容易)
@brief 又要用volatile布尔变量来控制次线程
(用isInterrupted会因sleep出问题)
@note 所以要用interrupt来疏通阻塞,使得线程顺利获得volatile布尔变量
@addition
此处代码参考:
http://blog.csdn.net/wxwzy738/article/details/8516253
*/
运行效果