原创:转载需注明原创地址 https://www.cnblogs.com/fanerwei222/p/11398563.html

  notify() 和 wait() 主要是用来多个线程之间的协作。

  它们都是Object的方法,任何对象都可以调用这两个方法。

  首先设置一个多个线程共享的对象 :

//共享对象
Object shareObject = new Object();

  1.wait() :导致当前线程等待,直到另一个线程调用该对象的notify()或者notifyAll()方法;

  这里用代码解释一下:

class ThreadOne extends Thread{
@Override
public void run() {
synchronized (shareObject){
for (int i = 0; i < 10 ; i++){
System.out.println("A线程--->"+i);
shareObject.notify();
if (first){
first = false;
try {
shareObject.wait();
} catch (Exception e){
System.out.println(e);
}
}
}
}
}
}

  这里的 shareObject.wait(); 会导致ThreadOne线程进入shareObject对象的等待队列(这个等待队列可能会有多个线程,这些线程都停止继续执行,进入等待状态),直到其他线程调用shareObject的notify()或者notifyAll()方法,ThreadOne线程就可能会被唤醒,因为该唤醒是从等待队列中随机抽取一个线程进行唤醒,不公平唤醒。

  2.notify() :唤醒正在等待对象监视器的单个线程。这个在上面已经作了解释,下面用代码说明一下。

class ThreadTwo extends Thread{
@Override
public void run() {
synchronized (shareObject){
for (int i = 0; i < 10; i++){
System.out.println("B线程--->"+i);
shareObject.notify();
if (!first){
first = true;
try {
shareObject.wait();
}catch (Exception e){
System.out.println(e);
}
}
}
}
}
}

  这里的 shareObject.notify();会从shareObject对象的等待队列中随机唤醒一个线程,但是目前的shareObject对象的等待队列中只有ThreadOne一个线程,所以它就被唤醒了。

  过程如下图:

  

    最后:wait和sleep区别

  

    1️⃣ wait和sleep方法都可以让线程等待;

    2️⃣ wait()方法可以被唤醒,sleep不能被唤醒。

    3️⃣ wait()既会释放cpu,也会释放共享资源的锁,sleep()不会释放任何资源。

    4️⃣ wait和sleep方法都可以使线程进人阻塞状态。

    5️⃣ wait和sleep方法均是可中断方法,被中断后都会收到中断异常。

    6️⃣ wait是Object的方法,而sleep是Thread特有的方法。

    7️⃣ wait方法的执行必须在同步方法中进行,而sleep则不需要。

    8️⃣ 线程在同步方法中执行sleep方法时,并不会释放monitor的锁,而wait方法则会释放monitor的锁。

    9️⃣ sleep方法短暂休眠之后会主动退出阻塞,而wait方法(没有指定wait时间)则需要被其他线程中断后才能退出阻塞。

     sleep:是Thread的静态方法,会使当前线程释放cpu,但不会释放锁资源,可以理解为只和cpu有关,不涉及锁资源。涉及锁资源的,是wait,join方法。

    1️⃣ yield:也是Thread的静态方法,和sleep方法类似,会使当前线程释放cpu,但不会释放锁资源。和sleep不同的是,sleep必须设置时间,但是yield不能设置时间,时间值是随机的

    2️⃣ join: 等待join方法执行线程先执行完毕, main方法再继续执行; 例如 main方法中有一个线程thread执行了thread.join() ; 那么当main方法执行到了thread.join()语句时,必须等待thread线程执行完毕,才能继续执行;thread必须执行了start方法才会这样,如果没有执行start方法main方法会直接执行下去.

    结束

notify()和wait()的更多相关文章

  1. Thread Object wait() notify()基本

    package com.thread.test.thread; import java.util.ArrayDeque; import java.util.Queue; import java.uti ...

  2. 如何在 Java 中正确使用 wait, notify 和 notifyAll(转)

    wait, notify 和 notifyAll,这些在多线程中被经常用到的保留关键字,在实际开发的时候很多时候却并没有被大家重视.本文对这些关键字的使用进行了描述. 在 Java 中可以用 wait ...

  3. java多线程wait notify join

    wait notify 几个注意点: wait 与 notify/notifyAll 方法必须在同步代码块中使用,即要先对调用对象加锁. 当线程执行wait()时,会把当前的锁释放,然后让出CPU,进 ...

  4. 【Java并发系列02】Object的wait()、notify()、notifyAll()方法使用

    一.前言 对于并发编程而言,除了Thread以外,对Object对象的wati和notify对象也应该深入了解其用法,虽然知识点不多. 二.线程安全基本知识 首先应该记住以下基本点,先背下来也无妨: ...

  5. 【多线程】java多线程 测试例子 详解wait() sleep() notify() start() join()方法 等

    java实现多线程,有两种方法: 1>实现多线程,继承Thread,资源不能共享 2>实现多线程  实现Runnable接口,可以实现资源共享 *wait()方法 在哪个线程中调用 则当前 ...

  6. #研发中间件介绍#异步消息可靠推送Notify

    郑昀 基于朱传志的设计文档 最后更新于2014/11/11 关键词:异步消息.订阅者集群.可伸缩.Push模式.Pull模式 本文档适用人员:研发   电商系统为什么需要 NotifyServer? ...

  7. 线程同步以及 yield() wait()和notify()、notifyAll()

    1.yield() 该方法与sleep()类似,只是不能由用户指定暂停多长时间,并且yield()方法只能让同优先级的线程有执行的机会. 2.wait()和notify().notifyAll() 这 ...

  8. java 多线程之wait(),notify,notifyAll(),yield()

    wait(),notify(),notifyAll()不属于Thread类,而是属于Object基础类,也就是说每个对像都有wait(),notify(),notifyAll()的功能.因为都个对像都 ...

  9. wait、notify、sleep、interrupt对比分析

    对比分析Java中的各个线程相关的wait().notify().sleep().interrupt()方法 方法简述 Thread类 sleep:暂停当前正在执行的线程:(类方法) yield:暂停 ...

  10. java中的wait(),notify(),notifyAll(),synchronized方法

    wait(),notify(),notifyAll()三个方法不是Thread的方法,而是Object的方法.意味着所有对象都有这三个方法,因为每个对象都有锁,所以自然也都有操作锁的方法了.这三个方法 ...

随机推荐

  1. Go 通过 Map/Filter/ForEach 等流式 API 高效处理数据

    什么是流处理 如果有 java 使用经验的同学一定会对 java8 的 Stream 赞不绝口,极大的提高了们对于集合类型数据的处理能力. int sum = widgets.stream() .fi ...

  2. 数据库SQL语言类型(DQL.DML.DDL.DCL)

    1.SQL语言 SQL(Structure Query Language)语言是数据库的核心语言. SQL是一个标准的数据库语言, 是面向集合的描述性非过程化语言. 它功能强,效率高,简单易学易维护. ...

  3. mysql编译报错

    1.make报错现象 Warning: Bison executable not found in PATH 解决办法 yum -y install bison 2.make报错现象 ake Erro ...

  4. Microsoft HoloLens 开发(3): 全息图交互方式 - Gaze

    Gaze(凝视) 是 HoloLens 交互输入的第一种形式,告诉你 用户 在世界上的位置,并让你确定他们的意图. 1.Gaze的用途 作为一个 Mixed Reality 开发者,Gaze 可以做很 ...

  5. GOF23种设计模式之单例模式(java)

    GOF(group of four):四人帮 分类 创建者模式 单例模式 核心作用:保证一个类只有一个实例,并且提供一个访问该实例的全局访问点 优点: 由于单例模式只生成一个实例,减少了系统性能开销, ...

  6. HDU 1106 (1.3.5) 排序 (C语言描述)

    排序 Problem Description 输入一行数字,如果我们把这行数字中的'5'都看成空格,那么就得到一行用空格分割的若干非负整数(可能有些整数以'0'开头,这些头部的'0'应该被忽略掉,除非 ...

  7. vue3+vant h5: Rem 移动端布局适配之postcss-pxtorem和lib-flexible

    如果不引入插件的话:ui稿的px转化成rem需自己计算 根据设计稿我们需要自己计算元素的rem(假如我们将html根元素font-size设置为41.4px): 那么1rem=41.4px; ui稿上 ...

  8. 小白也能看懂的Redis教学基础篇——做一个时间窗限流就是这么简单

    不知道ZSet(有序集合)的看官们,可以翻阅我的上一篇文章: 小白也能看懂的REDIS教学基础篇--朋友面试被SKIPLIST跳跃表拦住了 书接上回,话说我朋友小A童鞋,终于面世通过加入了一家公司.这 ...

  9. Mybatis 学习记录

    1.先放上mybatis官网地址: https://mybatis.org/mybatis-3/zh/index.html 2.mybatis源码和有关包下载地址(GitHub): https://g ...

  10. sql中常用到的GUID

    在项目的数据库中经常见到如下所示的列: 列名:**_id 数据类型:UNIQUEIDENTIFIER 默认:NEWID() ROWGUIDCOL 属性. 其实这样的列通常为表的主键,函数NEWID() ...