notify(通知)方法,会将等待队列中的一个线程取出。比如obj.notify();那么obj的等待队列中就会有一个线程选中并且唤醒,然后被唤醒的队列就会退出等待队列。活跃线程调用等待队列中的线程时,因为现在的活跃线程还用有锁,会先将synchronized代码块执行完毕,释放对象监视器,被唤醒的线程才会获得这个监视器,然后被唤醒的线程才能继续执行。也就是说原来在等待队列中的线程被唤醒后,在被执行notify的一瞬间并不会立刻执行,因为在被执行notify的一瞬间,原来执行notify的线程还持有着锁,所以其他线程还无法获取这个实例的锁。

举个例子:假设熊大和熊二都要到小黑屋里面壁十分钟,小黑屋同一时刻只能允许一只熊进行面壁思过。熊大先进开始面壁思过同时把门锁上(相当于执行synchronized代码块拥有锁),结果在熊大面壁到三分钟的时候,困了想去睡觉(相当于执行wait()方法,进去到等待队列),这时它走出了门(相当于释放锁)去睡觉,熊二开始进来进行面壁思过,当熊二面壁到6分钟的时候,喊了一声让熊大接着来面壁思过(相当于执行notify方法),因为熊二还在继续面壁思过,所以熊大要在小黑屋外一直等,等到熊二面壁结束后(释放了锁),才能进去接着面壁,面壁剩余的七分钟,所以说即使熊二在第6分钟叫醒了熊大,但因为此时熊二在小黑屋里,熊大也不可能第一时间面壁思过。

如果说等待队列中的线程不止一个,那么当执行notify的时候叫醒那一个呢,被唤醒的线程是随机选择的。那么被唤醒的线程在作为锁定此对象的下一个线程方面没有可靠的特权或劣势。

notifyAll(通知全部)方法是将等待队列中的所以线程都唤醒,用法和notify一样。区别是notify只能唤醒等待队列中的一个,而notifyAll却能唤醒等待队列中的全部。

在实际使用时,是使用notify还是notifyAll,那个更好呢。

因为notify唤醒的线程比notifyAll少,所以notify的处理速度会更快。

使用notifyAll的代码要比使用notify的代码更健壮,因为使用notify如果处理不好,程序便有可能终止。

wait() ,notify()和notifyAll()方法都要获得此对象的监视器,也就是要获得锁,否则会报IllegalMonitorStateException异常

java线程学习之notify方法和notifyAll方法的更多相关文章

  1. Object类中wait代餐方法和notifyAll方法和线程间通信

    Object类中wait代餐方法和notifyAll方法 package com.yang.Test.ThreadStudy; import lombok.SneakyThrows; /** * 进入 ...

  2. java数组、java.lang.String、java.util.Arrays、java.lang.Object的toString()方法和equals()方法详解

    public class Test { public static void main(String[] args) { int[] a = {1, 2, 4, 6}; int[] b = a; in ...

  3. JAVA反射中的getFields()方法和getDeclaredFields ()方法的区别

    JAVA反射中的getFields()方法和getDeclaredFields ()方法的区别   关于获取类的字段有两种方式:getFields()和getDeclaredFields().我们先来 ...

  4. Object类中wait带参方法和notifyAll方法和线程间通信

    notifyAll方法: 进入到Timed_Waiting(计时等待)状态有两种方式: 1.sleep(long m)方法,在毫秒值结束之后,线程睡醒,进入到Runnable或BLocked状态 2. ...

  5. Java Thread中,run方法和start方法的区别

     两种方法的区别: 1.start方法 用 start方法来启动线程,是真正实现了多线程, 通过调用Thread类的start()方法来启动一个线程,这时此线程处于就绪(可运行)状态,并没有运行,一旦 ...

  6. [转]JAVA反射中的getFields()方法和getDeclaredFields ()方法的区别

    关于获取类的字段有两种方式:getFields()和getDeclaredFields().我们先来看看这两者的区别吧: getFields():获得某个类的所有的公共(public)的字段,包括父类 ...

  7. java.util.Scanner中hasNext()方法和next()方法的区别

    先说结论: 两者均根据空格划分数据 两者在没有数据输入时均会等待输入 next()方法会将空格划分的数据依次输出,运行一次,输出一个 hasNext()方法会跟着next()方法移动,当前数据不为空, ...

  8. Java中Scanner中nextLine()方法和next()方法的区别

    https://blog.csdn.net/hello_word2/article/details/54895106

  9. Object、String、数组的 toString() 方法和 equals() 方法及java.util.Arrays

    public class Test { public static void main(String[] args) { int[] a = {1, 2, 4, 6}; int[] b = a; in ...

随机推荐

  1. [LeetCode] K-th Symbol in Grammar 语法中的第K个符号

    On the first row, we write a 0. Now in every subsequent row, we look at the previous row and replace ...

  2. 6.6 Pandora 实操 - API/SDK

    创建实时仓库 连接日志仓库 点击到工作流查看 通过 Java sdk 打数据 通过 java sdk 对应字段打数据,先打到实时仓库(消息队列),对应再会打到日志仓库(做存储). 代码见 Sequen ...

  3. react路由

    针对多个列表导航公用一个组建,然后 有两种路由方式 1.import {HashRouter as Router,Route,Link} from 'react-router-dom' 不过这个路由中 ...

  4. verilog中signed的使用

    1.在verilog中有时会用signed修饰符来修饰定义的数据,运算的时候也会用$signed()任务来强制转换数据,那么signed的修饰是为什么呢,是为了区分有符号数和无符号数的加法和乘法吗?其 ...

  5. jenkins测试配置

  6. 壁虎书8 Dimensionality Reduction

    many Machine Learning problems involve thousands or even millions of features for each training inst ...

  7. vim模式下报错E37: No write since last change (add ! to override)

    故障现象: 使用vim修改文件报错,系统提示如下: E37: No write since last change (add ! to override) 故障原因: 文件为只读文件,无法修改. 解决 ...

  8. js 转java后台传过来的list

    var intIndex=0; arrList = new Array(); arrList = "${orderNumList}".replace('[','').replace ...

  9. git 解决授权失败的方法

    git 提示  fatal: Authentication failed for 'http://***********‘’得解决方法 首先用 git config --list 查看一下 如果不对, ...

  10. raise error

    raise TypeError("参数q_type 错误 ")