java线程——中断线程+线程状态+线程属性(优先级)

【0】README

0.1) 本文描述转自 core java volume 1, 源代码为原创,旨在理解 java线程——中断线程+线程状态+线程属性(优先级) 的相关知识;


【1】中断线程

1.1)当线程的run方法执行方法体中最后一条语句后, 并经由return语句返回时, 或出现了在方法中没有捕获的异常时,线程将终止;
1.2)强制线程终止: interrupt 方法可以用来请求终止线程;

  • 1.2.1)判断线程是否已经终止: Thread.currentThread().isInterrupted()
  • 1.2.2)但是,如果线程被阻塞, 就无法检测中断状态,这是产生 InterruptedException异常的地方;
public void run()
{
    try
    {
        while(!Thread.currentThread().isInterrupted())
            .....
    }
    catch(){}
    finally(){}
}
  • 1.2.3)中断状态时的线程调用 sleep, 不仅不会休眠, 相反, 抛出IntertupptedException;

Annotation)有两个非常类似的方法, interrupted 和 isInterrupted

  • A1)Interrupted 方法是一个静态方法: 它检测当前的线程是否中断, 而且,该方法会清除该线程的中断状态;
  • A2)isInterrupted 方法是一个实例方法: 可用来检验是否有线程被中断, 调用这个方法不会改变中断状态;

1.3)有两种方法用来抛出 InterrupttedException

  • 1.3.1)在catch 子句中调用 Thread.currentThread().interrrupt() 来设置中断状态;
void fun()
{
    try{}
    catch()
    { Thread.currentThread().interrupte();}
}
  • 1.3.2)或者用throws 标记你的方法, 不采用 try 语句块捕获这个异常
void func() throws InterruptedException
{
    sleep(delay);
}

【2】线程状态

2.1)线程有6种状态(status):

  • S1) new(新创建);
  • S2) Runnable(可运行);
  • S3) Blocked(被阻塞);
  • S4) Waiting(等待);
  • S5) Timed waiting(计时等待);
  • S6) Terminated(被终止);
  • Attention)记住, 在任何时刻,一个可运行线程可能正在运行也可能没有运行(这就是为什么将这个状态称为 可运行而不是 运行);

【3】被阻塞线程和等待线程

3.1)阻塞状态:当一个线程试图获取一个内部的对象锁,而该锁被其他线程持有, 则该线程进入阻塞状态;
3.2)等待状态:当线程等待另一个线程通知调度器一个条件时, 它进入等待状态;(在调用 Object.wait 或 Thread.join 方法 或是等待java.util.concurrent 库中的Lock 或 Condition时, 就会出现这种case);
3.3)超时参数:调用它们导致线程进入计时等待状态, 这一状态将一直保持到超时期满或者接收到适当的通知, 方法有:Thread.sleep , Object.wait, Thread.join, Lock.tryLock ,Condition.await;


【4】被终止的线程

4.0)终止的原因(Reasons):

  • R1)因为run方法正常退出而终止;
  • R2)因为一个没有捕获的异常终止了run方法而意外死亡;
    这里写图片描述

  • M1)start方法:开启线程(抑或是分配CPU), 它执行Runnable接口的 run 方法;

  • M2)yield()方法的作用是:暂停当前正在执行的线程对象,并执行其他线程。;
  • M3)Thread的非静态方法join()方法:让一个线程B“加入”到另外一个线程A的尾部。在A执行完毕之前,B不能工作。例如:
Thread t = new MyThread();
t.start();
t.join();
  • M3.1)另外,join()方法还有带超时限制的重载版本。 例如t.join(5000);则让线程等待5000毫秒,如果超过这个时间,则停止等待,变为可运行状态。
    线程的加入join()对线程栈导致的结果是线程栈发生了变化,当然这些变化都是瞬时的。下面给示意图
    这里写图片描述
  • M4)Thread.sleep方法: 使当前线程睡眠至少多少毫秒
  • M5) void notify() : 唤醒在此对象监视器上等待的单个线程。
  • M6) void notifyAll(): 唤醒在此对象监视器上等待的所有线程。
  • M7) void wait() :导致当前的线程等待,直到其他线程调用此对象的 notify() 方法或 notifyAll() 方法。
  • M8)synchronized : 同步方法或同步块的关键字;

【5】线程属性

5.1)线程优先级

  • 5.1.1)设置线程的优先级:线程默认的优先级是创建它的执行线程的优先级。可以通过setPriority(int newPriority)更改线程的优先级。例如:
Thread t = new MyThread();
t.setPriority(8);
t.start();
  • 线程优先级为1~10之间的正整数,JVM从不会改变一个线程的优先级。
    • 5.1.1.1)线程默认优先级是5,Thread类中有三个常量,定义线程优先级范围:
    • 5.1.1.2)static int MAX_PRIORITY :线程可以具有的最高优先级。
    • 5.1.1.3)static int MIN_PRIORITY :线程可以具有的最低优先级。
    • 5.1.1.4)static int NORM_PRIORITY :分配给线程的默认优先级 == 5。

5.2)守护线程

  • 5.2.1)通过调用 t.setDaemon(true) 来将线程转换为 守护线程(daemon thread);
  • 5.2.2)守护线程的唯一用途: 为其他线程提供服务;
  • 5.2.3)看个荔枝:计时线程就是一个荔枝。它定时发送“计时器滴答”信号给其他线程或清空过时的高速缓存项的线程。当只剩下守护线程时, 虚拟机就退出了,因为如果只有守护线程, 就没必要继续运行程序了;

5.3)未捕获异常处理器

  • 5.3.1)出现的问题: 线程的run方法不能抛出任何被检测的异常, 但是,不被检测的异常会导致线程死亡;
  • 5.3.2)解决方法:在线程死亡之前, 异常被传递到一个用于未捕获异常的处理器;
    • 5.3.2.1)该处理器必须属于一个实现了 Thread.UncaughtExceptionHandler 接口的类。 这个接口只有一个方法: void uncaughtExceptionHandler ;
    • 5.3.2.2)可以用 setUncaughtExceptionHandler 方法为任何线程安装一个 处理器。 也可以用 Thread的静态方法 setDefaultUncaughtExceptionHandler 为所有线程安装一个默认处理器;
    • 5.3.2.3)如果不安装默认的处理器, 默认处理器就为空。 但是,如果不为独立的线程安装处理器,此时的处理器就是该线程的 ThreadGroup 对象了;(但是建议,不要在程序中使用线程组 ThreadGroup);
  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值