您的位置 首页 java

Java线程调度&状态

摘要

  1. 什么是线程调度
  2. 协同式调度
  3. 抢占式调度
  4. 线程优先级
  5. 线程状态

1. 线程调度

1.1 什么是线程调度

线程调度是指系统为线程分配处理器使用权的过程。

1.2 协同式调度

线程的执行时间由线程本身控制,线程在工作完成以后要主动通知系统切换到另一个线程上。优点是实现简单、切换操作对线程自己可见,不存在线程同步问题;缺点是线程时间不可控制,有可能造成程序一直阻塞。

1.2 抢占式调度

线程由操作系统来分配执行时间,线程的切换不会由线程本身决定。优点是线程执行时间可控;缺点则是需要进行线程同步。

Java中的线程采用的是抢占式调度的实现方式。

2. 线程优先级

线程优先级是用来表示线程获得CPU资源的可能性,线程优先级越高,系统更容易为其分配处理器去执行。

Java中的线程优先级不太靠谱,原因是Java定义了大约10个级别的优先级,最小的优先级为1,最高优先级为10,线程的优先级默认与父线程一致,假设操作系统线程的优先级的级别层次比Java少(最小1,最大5),那么在映射以后,Java两个不同优先级的优先级有可能共同对应操作系统的同一个优先级。

3. 线程状态

Java线程大致有以下状态:

  1. New
  2. Runnable
  3. Waiting
  4. TimeWaiting
  5. Blocked
  6. Terminated

3.1 New

创建以后尚未启动的线程,new但未start

3.2 Runnable

Runnable的线程有可能在执行,也有可能等待着CPU为它分配执行时间

3.3 Waiting

线程不会被CPU分配执行时间,需要其他线程显示唤醒。以下方法会让线程进入Waiting状态:

  • 没有Timeout的Object.wait()
  • 没有Timeout的 thread .join()
  • LockSupport.park()方法

3.4 TimeWaiting

线程不会被CPU分配执行时间,可以被其他线程显示唤醒,一定时间后没有其他线程唤醒,将会由操作系统主动唤醒。以下方法会让线程进入TimeWaiting状态:

  • Thread.sleep()
  • 设置了Timeout的Object.wait()
  • 设置了Timeout的Thread.join()
  • LockSupport.parkNanos()
  • LockSupport.parkUntil()

3.5 Blocked

线程处于阻塞状态,阻塞状态的线程在等待着获取到一个排他锁。在程序等待进入同步区域的时候,线程将进入这种状态

3.6 Terminate

线程执行结束以后的状态。

 package jvm;

/**
 * @author sh
 */public class ThreadTest  implements  Runnable {


    @ Override 
    public  void  run() {
        try {
            Thread.sleep(Integer.MAX_VALUE);
        } catch (InterruptedException e) {
            e.printStackTrace();
        }
    }

    public  static  void main(String[] args) throws InterruptedException {
        ThreadTest threadTest = new ThreadTest();
        Thread thread = new Thread(threadTest, "TEST-1");
        thread.start();
        thread.join();
    }
}
  

上述代码首先根据前文我们的描述,我们可以得出,主线程应该是Waiting(由于Thread.join()方法的调用),TEST-1线程应该是TimeWaiting状态(通过Thread.sleep()方法的调用)。

下面我们通过jstack命令看一下我们的堆栈是不是和我们分析的结果一致:

 public class ThreadTest implements Runnable {

    private final Object syncObj = new Object();


    @Override
    public void run() {
         synchronized  (syncObj) {
            try {
                Thread.sleep(Integer.MAX_VALUE);
            } catch (InterruptedException e) {
                e.printStackTrace();
            }
        }
    }

    public static void main(String[] args) throws InterruptedException {
        ThreadTest threadTest = new ThreadTest();
        Thread t1 = new Thread(threadTest, "TEST-1");
        Thread t2 = new Thread(threadTest, "TEST-2");
        t1.start();
        Thread.sleep(1L);
        t2.start();
        t1.join();
    }
}
  

上述这段代码,TEST-1线程应该是TimeWaiting,TEST-2线程应该是BLOCK状态,主线是Waiting状态,下面我们通过jstack命令来看一下:

本期的Java线程调度和状态实现介绍到这,我是shysh95,我们下期再见!!

文章来源:智云一二三科技

文章标题:Java线程调度&状态

文章地址:https://www.zhihuclub.com/199825.shtml

关于作者: 智云科技

热门文章

网站地图