Java多线程阻塞与唤醒代码示例

发布时间 - 2026-01-11 03:27:30    点击率:

java线程的阻塞及唤醒

1. sleep() 方法:

sleep(…毫秒),指定以毫秒为单位的时间,使线程在该时间内进入线程阻塞状态,期间得不到cpu的时间片,等到时间过去了,线程重新进入可执行状态。(暂停线程,不会释放锁)

//测试sleep()方法
class Thread7 implements Runnable{
  @Override
  public void run() {
    for(int i=0;i<50;i++){
      System.out.println(Thread.currentThread().getName()+"num="+i);
      try {
        Thread.sleep(500);
      } catch (InterruptedException e) {
        e.printStackTrace();
      }
    }
  }
}
class Thread8 implements Runnable{
  @Override
  public void run() {
    for(int i=0;i<1000;i++){
      System.out.println(Thread.currentThread().getName()+"num="+i);
    }
  }
}
public static void main(String[] args) {
    /*
     * 测试线程阻塞
     */
    //测试sleep()方法
    Thread7 t7=new Thread7();
    Thread8 t8=new Thread8();
    Thread t81=new Thread(t8, "饺子");
    Thread t71=new Thread(t7, "包子");
    Thread t72=new Thread(t7, "面包");
    t71.start();
    t81.start();
    t72.start();
  }

2.suspend() 和 resume() 方法:。

挂起和唤醒线程,suspend()使线程进入阻塞状态,只有对应的resume()被调用的时候,线程才会进入可执行状态。(不建议用,容易发生死锁)

//测试suspend()和resume()方法
class Thread9 implements Runnable{
  @Override
  public void run() {
    for(long i=0;i<500000000;i++){
System.out.println(Thread.currentThread().getName()+" num= "+i);
    }
  }
}
public static void main(String[] args) {
  //测试suspend和resume
    Thread9 t9=new Thread9();
    Thread t91=new Thread(t9,"包子");
    t91.start();
    try {
      Thread.sleep(2000);
    } catch (InterruptedException e) {
      // TODO Auto-generated catch block
      e.printStackTrace();
    }
    t91.suspend();
    try {
      Thread.sleep(2000);
    } catch (InterruptedException e) {
      // TODO Auto-generated catch block
      e.printStackTrace();
    }
    t91.resume();
}

(在控制台打印输出的时候,会停顿2秒钟,然后再继续打印。)

3. yield() 方法:

会使的线程放弃当前分得的cpu时间片,但此时线程任然处于可执行状态,随时可以再次分得cpu时间片。yield()方法只能使同优先级的线程有执行的机会。调用 yield() 的效果等价于调度程序认为该线程已执行了足够的时间从而转到另一个线程。(暂停当前正在执行的线程,并执行其他线程,且让出的时间不可知)

//测试yield()方法
class Thread10 implements Runnable{
  @Override
  public void run() {
    for(int i=0;i<100;i++){
      System.out.println(Thread.currentThread().getName()+" num= "+i);
      if(i==33){
        Thread.yield();
      }
    }
  }
}

public static void main(String[] args) {
  //测试yield
    Thread10 t10 =new Thread10();
    Thread t101=new Thread(t10, "包子");
    Thread t102=new Thread(t10, "面包");
    t101.start();
    t102.start();
}
/*
运行结果为:
……
包子 num= 24
包子 num= 25
包子 num= 26
包子 num= 27
包子 num= 28
包子 num= 29
包子 num= 30
包子 num= 31
包子 num= 32
包子 num= 33
面包 num= 0
面包 num= 1
面包 num= 2
面包 num= 3
……
面包 num= 30
面包 num= 31
面包 num= 32
面包 num= 33
包子 num= 34
包子 num= 35
包子 num= 36
包子 num= 37
包子 num= 38
……
*/

(可以看到,当数字为33时,都发生了交替。)

4.wait() 和 notify() 方法:

两个方法搭配使用,wait()使线程进入阻塞状态,调用notify()时,线程进入可执行状态。wait()内可加或不加参数,加参数时是以毫秒为单位,当到了指定时间或调用notify()方法时,进入可执行状态。(属于Object类,而不属于Thread类,wait( )会先释放锁住的对象,然后再执行等待的动作。由于wait( )所等待的对象必须先锁住,因此,它只能用在同步化程序段或者同步化方法内,否则,会抛出异常IllegalMonitorStateException.)

//测试wait()和notify()方法
//用生产者和消费者模式模拟这一过程
/*消费者 */
class Consumer implements Runnable {
private Vector obj;
  public Consumer(Vector v) {
    this.obj = v;
  }
  public void run() {
    synchronized (obj) {
      while (true) {
        try {
          if (obj.size() == 0) {
            obj.wait();
          }
          System.out.println("消费者:我要买面包。");
          System.out.println("面包数: " + obj.size());
          obj.clear();
          obj.notify();
        } catch (Exception e) {
          e.printStackTrace();
        }
      }
    }
  }
}
/* 生产者 */
class Producter implements Runnable {
  private Vector obj;
  public Producter(Vector v) {
    this.obj = v;
  }
  public void run() {
    synchronized (obj) {
      while (true) {
        try {
          if (obj.size() != 0) {
            obj.wait();
          }
          obj.add(new String("面包"));
          obj.notify();
          System.out.println("生产者:面包做好了。");
          Thread.sleep(500);
        } catch (Exception e) {
          e.printStackTrace();
        }
      }
    }
  }
}
public static void main(String[] args) {
  //测试wait()和notify()
    Vector obj = new Vector();
    Thread consumer = new Thread(new Consumer(obj));
    Thread producter = new Thread(new Producter(obj));
    consumer.start();
    producter.start();
}

5.join()方法

也叫线程加入。是当前线程A调用另一个线程B的join()方法,当前线程转A入阻塞状态,直到线程B运行结束,线程A才由阻塞状态转为可执行状态。

//测试join
class Thread11 implements Runnable{
  @Override
  public void run() {
    System.out.println("Start Progress.");
    try {
      for(int i=0;i<5;i++){
        System.out.println("Thread11线程 : "+i);
        Thread.sleep(1000);
      }
    } catch (InterruptedException e) {
      // TODO Auto-generated catch block
      e.printStackTrace();
    }
    System.out.println("End Progress.");
  }
}
public static void main(String[] args) {
  //测试join
    Thread11 t11=new Thread11();
    Thread t111=new Thread(t11);
    t111.start();
    try {
      t111.join();
    } catch (InterruptedException e) {
      // TODO Auto-generated catch block
      e.printStackTrace();
    }
    System.out.println("hi,I'm Main线程");
}
/*
运行结果为:
Start Progress.
Thread11线程 : 0
Thread11线程 : 1
Thread11线程 : 2
Thread11线程 : 3
Thread11线程 : 4
End Progress.
hi,I'm Main线程
*/

总结

本文关于Java多线程阻塞与唤醒代码示例的介绍就到这里,希望对大家学习Java有所帮助。感兴趣的朋友可以继续参阅:Java多线程ForkJoinPool实例详解 、 Java通过卖票理解多线程 、 Java线程安全基础概念解析等。有什么问题可以随时留言,或者有什么方面想要了解的,您也可以留言,小编会及时给您答复。希望大家对多多支持!


# java  # 多线程  # 阻塞  # 唤醒  # java多线程  # 示例  # Java多线程中停止线程遇到线程阻塞的处理方法详解  # Java的线程阻塞、中断及优雅退出方法详解  # Java线程阻塞和唤醒的几种方式详解  # Java线程阻塞的方法区别详解  # java调用process线程阻塞问题的解决  # java实现线程阻塞式方法  # 可执行  # 有什么  # 然后再  # 死锁  # 锁住  # 这一  # 才会  # 感兴趣  # 转到  # 而不  # 时间内  # 给您  # 可以看到  # 希望大家  # 会使  # 能使  # 就到  # 用在  # 不加 


相关栏目: 【 网站优化151355 】 【 网络推广146373 】 【 网络技术251813 】 【 AI营销90571


相关推荐: 如何快速上传自定义模板至建站之星?  详解Huffman编码算法之Java实现  千问怎样用提示词获取健康建议_千问健康类提示词注意事项【指南】  Windows Hello人脸识别突然无法使用  Windows家庭版如何开启组策略(gpedit.msc)?(安装方法)  Laravel如何实现API速率限制?(Rate Limiting教程)  无锡营销型网站制作公司,无锡网选车牌流程?  香港服务器建站指南:外贸独立站搭建与跨境电商配置流程  ChatGPT常用指令模板大全 新手快速上手的万能Prompt合集  Laravel怎么实现搜索功能_Laravel使用Eloquent实现模糊查询与多条件搜索【实例】  昵图网官方站入口 昵图网素材图库官网入口  Laravel怎么实现验证码(Captcha)功能  标题:Vue + Vuex + JWT 身份认证的正确实践与常见误区解析  Android Socket接口实现即时通讯实例代码  Python自动化办公教程_ExcelWordPDF批量处理案例  Laravel数据库迁移怎么用_Laravel Migration管理数据库结构的正确姿势  Laravel怎么进行浏览器测试_Laravel Dusk自动化浏览器测试入门  高端建站如何打造兼具美学与转化的品牌官网?  如何快速生成ASP一键建站模板并优化安全性?  Laravel如何获取当前登录用户信息_Laravel Auth门面使用与Session用户读取【技巧】  魔毅自助建站系统:模板定制与SEO优化一键生成指南  手机软键盘弹出时影响布局的解决方法  rsync同步时出现rsync: failed to set times on “xxxx”: Operation not permitted  Java Adapter 适配器模式(类适配器,对象适配器)优缺点对比  Laravel怎么在Blade中安全地输出原始HTML内容  1688铺货到淘宝怎么操作 1688一键铺货到自己店铺详细步骤  Win11怎样安装网易有道词典_Win11安装词典教程【步骤】  laravel服务容器和依赖注入怎么理解_laravel服务容器与依赖注入解析  详解Oracle修改字段类型方法总结  如何快速搭建FTP站点实现文件共享?  网站制作大概多少钱一个,做一个平台网站大概多少钱?  Python进程池调度策略_任务分发说明【指导】  Mybatis 中的insertOrUpdate操作  如何撰写建站申请书?关键要点有哪些?  网站视频制作书签怎么做,ie浏览器怎么将网站固定在书签工具栏?  C++用Dijkstra(迪杰斯特拉)算法求最短路径  PHP正则匹配日期和时间(时间戳转换)的实例代码  制作公司内部网站有哪些,内网如何建网站?  三星网站视频制作教程下载,三星w23网页如何全屏?  Laravel怎么创建控制器Controller_Laravel路由绑定与控制器逻辑编写【指南】  Laravel的辅助函数有哪些_Laravel常用Helpers函数提高开发效率  如何在Windows服务器上快速搭建网站?  Win11怎么恢复误删照片_Win11数据恢复工具使用【推荐】  UC浏览器如何切换小说阅读源_UC浏览器阅读源切换【方法】  如何在阿里云高效完成企业建站全流程?  如何使用 jQuery 正确渲染 Instagram 风格的标签列表  laravel怎么通过契约(Contracts)编程_laravel契约(Contracts)编程方法  Windows10如何删除恢复分区_Win10 Diskpart命令强制删除分区  桂林网站制作公司有哪些,桂林马拉松怎么报名?  微信小程序制作网站有哪些,微信小程序需要做网站吗?