资讯专栏INFORMATION COLUMN

Thread

Hujiawei / 2654人阅读

摘要:线程状态内部枚举类还未可运行状态运行状态。无限期等待状态。注意,这只是一个,可能无实质影响。线程中断中断线程判断是否被中断判断是否被中断,并清除当前中断状态的中断是一种协作机制。仅仅只是将线程的中断状态置为,该中断状态由方法设置。

Daemon Thread

Java中有两类线程:User Thread(用户线程)、Daemon Thread(守护线程,后台一些系统性的服务,比如垃圾回收线程、JIT线程) 。
如果 User Thread已经全部退出运行了,只剩下Daemon Thread存在了,那么虚拟机也就退出了(不管Daemon Thread是否结束)。

设置守护线程:

Thread daemonTread = new Thread();  
daemonThread.setDaemon(true);  //必须在thread.start()之前设置,否则会跑出一个IllegalThreadStateException异常。
daemonThread.isDaemon();  //检验守护线程。

在Daemon线程中产生的新线程也是Daemon的。 

线程状态

Thread内部枚举类:

 public enum State { 
        NEW, //还未start()   
        RUNNABLE, //(可运行状态、运行状态。到底是哪个状态由CPU时间片轮转来决定,轮到了就是运行状态,没轮到就是可运行状态。)
        BLOCKED, //阻塞状态。申请某些锁或某个对象的监视器,线程会被阻塞住。
        WAITING, //无限期等待状态。调用了wait方法。进入Waiting状态的线程会等待其他线程给它notify,通知到之后由Waiting状态又切换到Runnable状态继续执行。
        TIMED_WAITING, //有限期等待状态。等待xx秒还是没有被notify,则自动切换到Runnable状态。
        TERMINATED; //结束状态。
    }

注:在实例化线程并start()之后,线程是进入可运行状态。

API

线程优先级:
并不一定是高优先级一定先完成。只是高优先级完成的概率比较大,但是低优先级还是有可能先完成的。

Thread.yield()

Thread.yield()只是对CPU的一个暗示,暗示当前线程可让出运行位置(从运行状态转到可运行状态),让其他线程占用CPU核心。注意,这只是一个hint,可能无实质影响。也就是说不能保证当前运行的线程立即转化到可运行状态。

Thread.join()

 
Thread t = new Thread(() -> {
    //do something
});

t.start();
t.join(1000);    //等待线程t结束或1000毫秒

join本质是Object.wait(long timeout),即当前线程(主线程)进入waiting状态,监控对象为t。当一个线程运行完成终止后,将会调用notifyAll方法去唤醒等待在该线程实例上的所有线程,该操作由JVM完成。

Object.wait(long timeout)

将当前线程进入waiting状态(释放了锁),直到调用Object.notify()或Object.notifyAll() 或时间超过timeout。

    synchronized (MonitorObject) { 
        // do something
        MonitorObject.wait();
        // do something
        MonitorObject.notifyAll();
    }

wait、notify、notifyAll方法必须在同步块中(正在监视对象)。

sleep和wait主要区别:
sleep方法没有释放锁,而wait方法释放了锁,使得其他线程可以使用同步控制块或者方法。

Object.notify()

Wakes up a single thread that is waiting on this object"s monitor. If any threads are waiting on this object, one of them is chosen to be awakened.
notifyAll()就是唤醒所有线程。

线程中断
public void Thread.interrupt() // 中断线程 
public boolean Thread.isInterrupted() // 判断是否被中断 
public static boolean Thread.interrupted() // 判断是否被中断,并清除当前中断状态

Java的中断是一种协作机制。也就是说Thread.interrupt()并不一定就中断了正在运行的线程,它只是要求线程自己在合适的时机中断自己。
interrupt()仅仅只是将线程的中断状态置为true,该中断状态由native方法interrupt0()设置。

interrupt()只针对3种情况:

If this thread is blocked in an invocation of the wait(), wait(long), or wait(long, int) methods of the Object class, or of the join(), join(long), join(long, int), sleep(long), or sleep(long, int), methods of this class, then its interrupt status will be cleared and it will receive an InterruptedException.

If this thread is blocked in an I/O operation upon a java.nio.channels.InterruptibleChannel then the channel will be closed, the thread"s interrupt status will be set, and the thread will receive a java.nio.channels.ClosedByInterruptException.

If this thread is blocked in a java.nio.channels.Selector then the thread"s interrupt status will be set and it will return immediately from the selection operation, possibly with a non-zero value, just as if the selector"s wakeup method were invoked.
对于其他情况,只会将线程中断状态置为true。

对于非阻塞线程,只是改变了中断状态,并不会使线程停止:

    Thread nonBlocking = new Thread(() -> {
        while (true) {
            System.out.println("Produce -> ");// do something 
        }
    });

    nonBlocking.start();
    nonBlocking.interrupt();// this thread"s interrupt status will be set
    nonBlocking.join();

你应该这样做:

    Thread nonBlocking = new Thread(() -> {
        while (true) {
            if (Thread.currentThread().isInterrupted()) {
                System.out.println("Interrupted!");
                break;
            }

            System.out.println("Produce -> ");    /* do something */
        }
    });

//

    nonBlocking.start();
    Thread.sleep(10);        //确保第一次循环跑过if判断
    nonBlocking.interrupt();
    nonBlocking.join();

对于阻塞线程:

    Thread blocking = new Thread(() -> {
        while (true) {
            if (Thread.currentThread().isInterrupted()) {
                System.out.println("Interrupted!");
                break;
            }

            try {
                Thread.sleep(60_000);
            }
            catch (InterruptedException e) {
                System.out.println("InterruptedException When blocking");
                /*因为抛出异常后会清除中断状态,所以设置中断状态,从而使得下一个while循环if判断为true,跳出循环。*/
                Thread.currentThread().interrupt();
            }
        }
    });

//

    blocking.start();
    Thread.sleep(10);        //确保第一次循环跑过if判断
    blocking.interrupt();
    blocking.join();

文章版权归作者所有,未经允许请勿转载,若此文章存在违规行为,您可以联系管理员删除。

转载请注明本文地址:https://www.ucloud.cn/yun/67268.html

相关文章

  • Java实现线程的三种方式和区别

    摘要:下面我们通过代码来看一下实现和区别三种实现继承,重写方法实现接口,实现方法实现接口,实现方法,带有返回值和异常如何使用第一种实现方式第二种实现方式第三种实现从代码可以看出以上提到的区别,,。第二种方式并没有体现共用同一个。 Java实现线程的三种方式和区别 Java实现线程的三种方式: 继承Thread 实现Runnable接口 实现Callable接口 区别: 第一种方式继承T...

    hyuan 评论0 收藏0
  • java并发编程学习之synchronize(二)

    摘要:的应用方式代码块作用范围在中,作用对象是调用这个代码块的对象。方法进来了出来了运行的结果如下等把方法执行完,释放了的锁,才开始执行。静态方法运行的结果如下等待执行完才执行,说明是类锁类所的另外一种形式运行结果如下 synchronized的应用方式 代码块:作用范围在{}中,作用对象是调用这个代码块的对象。 方法:作用范围是一个方法,作用对象是调用这个方法的对象。 静态方法:作用范围...

    darkbaby123 评论0 收藏0
  • Java基础之线程Thread

    摘要:在程序开发中一定遇到并发编程的场景虽然我们大部分时间并不直接使用但是是多线程的基础面试中也会总是被问到与线程有关的问题那么线程都有哪些知识呢最近在研究线程的源码的时候也总结了关于线程一些基本知识线程是什么线程是轻量级的进程是操作系统调度任务 在程序开发中, 一定遇到并发编程的场景, 虽然我们大部分时间并不直接使用Thread, 但是Thread是多线程的基础, 面试中也会总是被问到与线...

    tomlingtm 评论0 收藏0
  • java 多线程基础, 我觉得还是有必要看看的

    摘要:主线程名我们启动的一个程序可以理解为一个进程一个进程中包含一个主线程线程可以理解为一个子任务中可以通过下面代码来获取默认的主线程名运行结果为这是线程的名字并不是方法通过此线程来执行方法而已两种方式创建线程继承类实现接口实现接口并且多线程运行 Java 主线程名 我们启动的一个程序可以理解为一个进程, 一个进程中包含一个主线程, 线程可以理解为一个子任务. Java 中可以通过下面代码来...

    kohoh_ 评论0 收藏0
  • CompletableFuture的执行线程

    默认使用的线程池 不传executor时默认使用ForkJoinPool.commonPool() IntStream.range(0, 15).parallel().forEach(i -> { System.out.println(Thread.currentThread()); }); 输出 Thread[ForkJoinPool.commonPoo...

    mo0n1andin 评论0 收藏0
  • (一)java多线程之Thread

    摘要:本人邮箱欢迎转载转载请注明网址代码已经全部托管有需要的同学自行下载类学习线程的开发者首先遇到的第一个类就是通过使用类我们就可以启动停止中断一个线程在同一个时间片里可能会有多个线程在执行每个线程都拥有它自己的方法调用堆栈参数和变量每个至少会有 本人邮箱: 欢迎转载,转载请注明网址 http://blog.csdn.net/tianshi_kcogithub: https://github...

    boredream 评论0 收藏0

发表评论

0条评论

最新活动
阅读需要支付1元查看
<