Java 线程停止

来源:互联网 发布:网络最火的捕鱼游戏 编辑:程序博客网 时间:2024/06/05 05:44

Java 线程停止的方法有三种目前学习到的。

  1. stop 方法。
  2. volatile 变量控制退出。
  3. interrupt 方法。

第一种方法官方不建议,这种停止方法会导致释放锁后线程工作来不及清理,从而会出现数据不一致。

第二种方法写了个代码学习,如下:

共享资源类:
package com.lenovo.plm.dms.p6;public class Service {        private volatile boolean requestedStoppedFlag = false;        private long record;        private String lock = new String();        public Service(long record){        this.record = record;    }        public void execute(){        synchronized (lock) {            while(true){                if(requestedStoppedFlag){                    return;                }                System.out.println(Thread.currentThread().getName() + " " +record++);            }                    }    }    public void stop(){                synchronized(this){            requestedStoppedFlag = true;            System.out.println(Thread.currentThread().getName() + " " +record++);        }    }}

线程类:
package com.lenovo.plm.dms.p6;public class MyThread extends Thread {        private Service service;        public MyThread(Service service){        this.service = service;    }        @Override    public void run() {       service.execute();    }}

执行类如下:

package com.lenovo.plm.dms.p6;public class Main {        public static void main(String[] args) {                Service service = new Service(0);                MyThread t1 = new MyThread(service);        t1.start();               try {            Thread.sleep(3000);        } catch (InterruptedException e) {            // TODO Auto-generated catch block            e.printStackTrace();        }                service.stop();    }}


这里创建了两个线程并发执行。主线程等待3s后,执行停止方法。执行后,线程结束。



第三种方法是用interrupt。见代码。
先创建service 共享资源的类。
package com.lenovo.plm.dms.p7;public class Service {        private long record;    private String lock = new String();        public Service(long record){        this.record = record;    }    public void execute(){                synchronized(lock){                        while(true){                if(Thread.interrupted()){                    return;                }                System.out.println(Thread.currentThread().getName() + " " + record++);            }        }    }  }

其次线程类
package com.lenovo.plm.dms.p7;public class MyThread extends Thread {    private Service service;        public MyThread(Service service){        this.service = service;    }        @Override    public void run() {        // TODO Auto-generated method stub        super.run();        service.execute();    }    }


最后调用:

package com.lenovo.plm.dms.p7;public class Main {        public static void main(String[] args) {                Service service = new Service(0);        MyThread t = new MyThread(service);        t.start();        try {            Thread.sleep(3000);        } catch (InterruptedException e) {            // TODO Auto-generated catch block            e.printStackTrace();        }                t.interrupt();                try {            t.join();            Thread.sleep(3000);        } catch (InterruptedException e) {            // TODO Auto-generated catch block            e.printStackTrace();        }                System.out.println(t.isAlive());            }}

执行结果是线程被停止了。



这三种方法理解如下:
第一种跳过。
第二种使用了volatile关键字,这个关键字可以保证线程每次读取该变量时,都是直接从主内存中读取,不会直接读线程内存中的值。这样,可以确保线程每次读到的值,都是最新的。因此有线程修改了这个变量,那么
当前执行的线程会马上知道,因此可以作为线程间通信的方法。

第三种使用了线程自身的方法来检查中断状态位。




0 0
原创粉丝点击