
获得徽章 0
- #读书打卡活动#
juejin.im
年前阅读完《Java多线程编程实战指南-核心篇》
线程切换
一个线程被剥夺处理器的使用权而被暂停运行就被称为切出;被操作系统选中占用处理器或者继续其运行就被称为切入。
切出和切入时,操作系统需要保存和恢复相应进程的进度信息,即上下文,一般包括通用寄存器的内容和程序计数器的内容。
一个Java线程的生命周期状态在RUNNABLE状态与非RUNNABLE状态之前切换的过程就是一个上下文切换的过程。
当一个线程的生命周期状态由RUNNABLE转换为非RUNNABLE时,这个线程被暂停,由非RUNNABLE状态进入RUNNABLE时,线程被唤醒。一个线程被唤醒仅代表该线程获得了一个继续运行的机会,而不代表其立刻可以占用处理器运行。
切换诱因
自发性上下文切换和非自发性上下文切换
1. 自发性上下文切换
Thread.sleep(long millis)
Object.wait()
Thread.yield()
Thread.join()
LockSupport.park()
此外,线程发生了(阻塞式)I/O操作或者等待其他线程持有的锁也会导致自发性上下文切换。
2. 非自发性上下文切换
由于线程调度器的原因被迫切出:包括线程时间片用完或者有一个更高优先级的线程需要被运行。 Java虚拟机的垃圾回收动作也可能导致非自发性上下文切换,因为回收过程需要暂停所有应用线程。
上下文切换开销
1. 直接开销
操作系统保存和恢复上下文所需的开销,主要是处理器时间开销
线程调度器进行线程调度的开销
2. 间接开销
处理器高速缓存重新加载的开销
上下文切换可能导致整个一级高速缓存的内容被Flush,即一级高速缓存中的内容被写入下一级高速缓存或主内存中。
从定量的角度来说,一次上下文切换的时间消耗是微秒级的。展开13