zoukankan      html  css  js  c++  java
  • 线程的生命周期

    一、线程的生命周期

    线程一个完整的生命周期要经历如下五种状态:

    • 新建:当一个Thread类或者其子类的对象被声明并创建时,新生的线程对象处于新建状态
    • 就绪:处于新建状态的西纳城被start()之后,将进入线程队列等待CPU时间片
    • 运行:当就绪的线程被调度并会的处理器资源时,便进入运行状态,run()方法定义了线程的操作和功能
    • 阻塞:在某种特殊情况下,被人为挂起挥着执行输入输出操作时,让出CPU并临时中止自己的执行,进入阻塞状态
    • 死亡:线程完成了它的全部工作或者线程被提前强制性的中止

    二、线程的生命周期状态转换图

    三、start方法源码分析

    上面的API文档是说,当我们调用线程的start方法时,JVM会调用当前线程的run()方法。这样就同时有两个线程在运行(当前线程和调用线程start()方法的线程)

    此外,同一个线程不能调用start()方法两次,否则会报错,IllegalThreadStateException 。

    (1)线程调用两次start()方法测试

    public static void main(String[] args) throws InterruptedException {
    
        Thread thread = new Thread(() -> {
            System.out.println("hello");
        });
    
        thread.start();
        thread.start();
    
    }

    输出结果:

    (2)start()内部源码分析

    public synchronized void start() {
         /**
         * This method is not invoked for the main method thread or "system"
         * group threads created/set up by the VM. Any new functionality added
         * to this method in the future may have to also be added to the VM.
         *
         * A zero status value corresponds to state "NEW".
         */
    
         //状态校验 0:NEW 新建状态
        if (threadStatus != 0)
            throw new IllegalThreadStateException();
    
        /* Notify the group that this thread is about to be started
         * so that it can be added to the group's list of threads
         * and the group's unstarted count can be decremented. */
       
         group.add(this);   // 添加进线程组 
    
        boolean started = false;
        try {
            start0(); //调用native方法执行线程run方法
            started = true;
        } finally {
            try {
                if (!started) {
                    group.threadStartFailed(this);  //启动失败,从线程组中移除当前前程。
                }
            } catch (Throwable ignore) {
                /* do nothing. If start0 threw a Throwable then
                  it will be passed up the call stack */
            }
        }
    }

    四、Thread的run()与start()的区别?

    该部分转自Thread的run()与start()的区别

    调用start()后,线程会被放到等待队列,等待CPU调度,并不一定要马上开始执行,只是将这个线程置于可动行状态。然后通过JVM,线程Thread会调用run()方法,执行本线程的线程体。先调用start后调用run,这么麻烦,为了不直接调用run?就是为了实现多线程的优点,没这个start不行。

    • start()方法来启动线程,真正实现了多线程运行。这时无需等待run方法体代码执行完毕,可以直接继续执行下面的代码;通过调用Thread类的start()方法来启动一个线程, 这时此线程是处于就绪状态, 并没有运行。 然后通过此Thread类调用方法run()来完成其运行操作的, 这里方法run()称为线程体,它包含了要执行的这个线程的内容, Run方法运行结束, 此线程终止。然后CPU再调度其它线程。
    • run()方法当作普通方法的方式调用。程序还是要顺序执行,要等待run方法体执行完毕后,才可继续执行下面的代码; 程序中只有主线程——这一个线程, 其程序执行路径还是只有一条, 这样就没有达到写线程的目的。

    记住:多线程就是分时利用CPU,宏观上让所有线程一起执行 ,也叫并发。

     

  • 相关阅读:
    软件工程最后一次作业
    软件工程第四次作业
    软件工程第三次作业
    软件工程第一次作业
    软件工程第二次作业
    软件工程第一次作业
    2020年最后一次软工作业
    2020年第四次软工作业(第二次结对作业)
    2020年第三次软工作业(第一次结对作业)
    2020年第二次软工作业
  • 原文地址:https://www.cnblogs.com/ch-forever/p/10747235.html
Copyright © 2011-2022 走看看