多线程之notify唤醒的随机性

本文通过修改《多线程核心技术》一书中的示例代码,实验Java中Notify方法唤醒线程的随机性。代码创建多个等待线程,观察哪些线程被随机唤醒,验证Notify是否如书中所述随机唤醒等待队列中的线程。

摘要生成于 C知道 ,由 DeepSeek-R1 满血版支持, 前往体验 >

在看多线程核心技术这本书的时候,里面提到了一句,notify()方法可以随机唤醒等待队列中等待统一资源的“一个一个线程”。突然很疑惑什么是统一共享资源,是不是随机。于是改动书上的代码实验一下,看一年运行结果。
原来代码如下

 package 线程间通信.wait_notify_size5;

import java.util.ArrayList;
import java.util.List;

/**
 * @Author:FuYouJie
 * @Date Create in 2019/11/11 23:17
 */
public class MyList {
    private static List list=new ArrayList();
    public static void add(){
        list.add("anyString");
    }
    public static int size(){
        return list.size();
    }
}
class  ThreadA extends Thread{
    private Object lock;
    public ThreadA(Object lock){
        super();
        this.lock=lock;
    }
    public void run(){
        try {
            synchronized (lock){
                if(MyList.size()!=5){
                    System.out.println("wait begin "+System.currentTimeMillis());
                    lock.wait();
                    System.out.println(Thread.currentThread().getName()+"运行了!");
                    System.out.println("wait end "+System.currentTimeMillis());
                }
            }
        } catch (InterruptedException e) {
            e.printStackTrace();
        }
    }
}
class ThreadB extends Thread{
    private Object lock;
    public ThreadB(Object lock){
        this.lock=lock;
    }
    public void run(){
        try {
            synchronized (lock){
                System.out.println(Thread.currentThread().getName()+"进来了!");
                for(int i=0;i<10;i++){
                    MyList.add();
                    if (MyList.size()==5){
                        lock.notify();
                        System.out.println("已发出通知!");
                    }
                    System.out.println("添加了"+(i+1)+"个元素");
                    Thread.sleep(500);
                }
            }
        } catch (InterruptedException e) {
            e.printStackTrace();
        }
    }
}
class Run{
    public static void main(String[] args) {
        try {
            Object lock=new Object();
            ThreadA a1=new ThreadA(lock);
            ThreadA a=new ThreadA(lock);
            a.setName("A");
            a.start();
            Thread.sleep(50);
            ThreadB b=new ThreadB(lock);
            b.start();
        } catch (InterruptedException e) {
            e.printStackTrace();
        }
    }
}

然后为了实验随机性,特意用数组生成多个A线程。
如下

class Run{
    public static void main(String[] args) {
        try {
            Object lock=new Object();
          /*  ThreadA a1=new ThreadA(lock);
            ThreadA a=new ThreadA(lock);
            a.setName("A");
            a.start();*/
          ThreadA []arr=new ThreadA[10];
          for(int i=0;i<10;i++){
              arr[i]=new ThreadA(lock);
              String name="a"+i+": ";
              arr[i].setName(name);
              arr[i].start();
          }
          //证明notify的随机性
            /*Thread-10进来了!
添加了1个元素
添加了2个元素
添加了3个元素
添加了4个元素
已发出通知!
添加了5个元素
添加了6个元素
添加了7个元素
添加了8个元素
添加了9个元素
添加了10个元素
a1: 运行了!
wait end 1573487544552uj
             */
            Thread.sleep(50);
            ThreadB b=new ThreadB(lock);
            b.start();
        } catch (InterruptedException e) {
            e.printStackTrace();
        }
    }
}

多运行几次,可以看到并不总是a0线程,被notify唤醒,同时试验了notifyAll();的确是所有线程被唤醒。
在这里插入图片描述
相关源码在我的Gihub
https://github.com/FuYouJ/Code-of-Java-Multi-thread-Programming
喜欢点个Star 明天早课,所以这里只有代码,没有分析。

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值