zoukankan      html  css  js  c++  java
  • 线程五大状态及其常用方法

    线程五大状态及其常用方法

    线程的五大状态

    生老病死乃人之常情,线程也是如此,当一个程序被执行开始,线程就开始了它的生命周期,直至程序运行结束,线程也随之死亡。

    线程的五大状态分别为:新建、就绪、运行、阻塞及死亡;

    五大状态的关系如下图所示:

    新建状态

    在生成线程对象之后,调用该对象的start方法之前,此时线程处于新建状态。

    就绪状态

    当调用了线程对象的start方法之后,该线程就进入了就绪状态,但是此时线程调度程序还没有把该线程设置为当前线程,即CPU还未调度这个线程进行运行,此时的线程就处于就绪状态。并且在线程开始运行之后,从等待或者睡眠中被激活之后,也会处于就绪状态。

    运行状态

    线程调度程序将处于就绪状态的线程设置为当前线程(线程被CPU调度),此时线程转为运行状态,开始运行重写的run()方法当中的代码。

    阻塞状态

    通常是为了等待某个事件的发生(比如说某项资源就绪)之后再继续运行(由运行状态转为阻塞状态)。sleep(),suspend(),wait()等方法都可以导致线程阻塞。

    死亡状态

    如果一个线程的run()方法执行结束或者调用stop()方法后,该线程就会死亡。对于已经死亡的线程,无法再使用start()方法令其进入就绪。

    常用方法

    sleep()——线程休眠

    • sleep(时间):指定当前进程阻塞的毫秒数;

    • sleep时间到达之后,线程进入就绪状态(等待CPU调度之后再执行);

    • sleep()可以模拟网络延时、倒计时等等;

    • 每一个对象都有一个锁,sleep不会释放锁。

    示例

    package state;

    import java.text.SimpleDateFormat;
    import java.util.Date;

    public class TestSleep {
       public static void main(String[] args) throws InterruptedException {
    //       Time time = new Time();
    //       time.time();

           DT dt = new DT();
           dt.date();
      }
    }

    //实现倒计时
    class Time{
       int num=20;
       public void time() throws InterruptedException {
           while(true){
               Thread.sleep(1000);
               System.out.println(num--);

               if(num<0)
                   break;
          }

      }
    }

    //实现日期时间的变化
    class DT{
       public void date() throws InterruptedException {
           Date date = new Date(System.currentTimeMillis());   //获取时间
           while(true){
               Thread.sleep(1000);
               System.out.println(new SimpleDateFormat("HH:mm:ss").format(date));
               date=new Date(System.currentTimeMillis());
          }
      }
    }

    yield()——线程礼让

    • 线程礼让是让当前正在执行的线程暂停,但不阻塞;

    • 将线程从运行状态转为就绪状态,同其他都属于就绪状态的线程一起再次接受CPU的调度;

    • 礼让后让CPU重新调度,但礼让不一定都能礼让成功(即让其他线程先执行),而是由CPU决定。

    示例

    package state;

    //线程礼让 yield();

    public class TestYield {
       public static void main(String[] args) {
           MyYield myYield = new MyYield();
           new Thread(myYield,"A ").start();
           new Thread(myYield,"B ").start();
      }
    }

    //线程类
    class MyYield implements Runnable{

       @Override
       public void run() {
           System.out.println(Thread.currentThread().getName()+"is running......");
           Thread.yield();     //线程礼让
           System.out.println(Thread.currentThread().getName()+"is stopped......");
      }
    }

    join()——线程强制执行

    • join方法可以让目标线程马上立即开始执行,待执行完成后再去执行被暂停的进程,这些被暂停的进程会暂时处于阻塞状态;

    • 简单理解:普通用户排队打饭,来了个VIP用户,直接插队(join()),其他普通用户只能等这个VIP打完饭才能继续打饭。

    示例

    package state;

    //join:线程强制执行

    public class TestJoin implements Runnable {


       @Override
       public void run() {
           System.out.println("老大来了,我可是VIP!!!");
      }

       public static void main(String[] args) throws InterruptedException {
           TestJoin testJoin = new TestJoin();
           Thread thread = new Thread(testJoin);
           thread.start();

           for (int i = 0; i < 200; i++) {
               if(i==150)
                   thread.join();      //线程强制执行   插队!!!
               System.out.println("Main"+i);
          }

      }
    }

    观测线程状态方法:getState()

    示例:(查看一个线程自新建至死亡的过程)

    package state;

    public class TestState implements Runnable {
       @Override
       public void run() {
           try {
               Thread.sleep(3000);
               System.out.println("123456789");
          } catch (InterruptedException e) {
               e.printStackTrace();
          }
      }

       public static void main(String[] args) throws InterruptedException {
           TestState testState = new TestState();
           Thread thread = new Thread(testState);

           //观测线程状态:
           Thread.State state = thread.getState();
           System.out.println(state);

           thread.start(); //启动线程
           state = thread.getState();  //获取启动后线程状态
           System.out.println(state);

           //观测线程状态:
           while (state != Thread.State.TERMINATED){
               Thread.sleep(100);
               state = thread.getState();
               System.out.println(state);

          }
      }
    }

    执行结果中表示线程生命周期的关键字:

    • NEW——尚未启动的进程处于此状态;

    • RUNNABLE——在Java虚拟机中运行的线程处于此状态;

    • BLOCKED——被阻塞等待监视器锁定的线程处于此状态;

    • WAITING——正在等在另一个线程执行特定动作的线程处于此状态;

    • TIMED-WAITING——正在等在另一个线程执行动作达到指定等待时间的线程处于此状态;

    • TERMINATED——已退出的线程处于此状态。

  • 相关阅读:
    Mybatis oracle多表联合查询分页数据重复的问题
    The Decade of Deep Learning
    D3S – A Discriminative Single Shot Segmentation Tracker
    Recent Advancements in NLP
    A list of datasets directly related to Music Information Retrieval Datasets
    Best Resources for Imbalanced Classification
    Attention-based Dropout Layer for Weakly Supervised Object Localization
    Learning a Discriminative Filter Bank within a CNN for Fine-grained Recognition
    Batch DropBlock Network for Person Re-identification and Beyond
    Cross-channel Communication Networks
  • 原文地址:https://www.cnblogs.com/awong18/p/13154201.html
Copyright © 2011-2022 走看看