Java多线程通信实现方式详解

 更新时间:2019年11月22日 11:00:01   作者:最喜欢夏天了  
这篇文章主要介绍了Java多线程通信实现方式详解,文中通过示例代码介绍的非常详细,对大家的学习或者工作具有一定的参考学习价值,需要的朋友可以参考下

这篇文章主要介绍了Java多线程通信实现方式详解,文中通过示例代码介绍的非常详细,对大家的学习或者工作具有一定的参考学习价值,需要的朋友可以参考下

线程通信的方式:

1、共享变量

线程间通信可以通过发送信号,发送信号的一个简单方式是在共享对象的变量里设置信号值。线程A在一个同步块里设置boolean型成员变量hasDataToProcess为true,线程B也在同步代码块里读取hasDataToProcess这个成员变量。这个简单的例子使用了一个持有信号的对象,并提供了set和get方法。

public class MySignal1 {
  //共享的变量
  private boolean hasDataToProcess = false;

  //取值
  public boolean getHasDataProcess() {
    return hasDataToProcess;
  }

  //存值
  public void setHasDataToProcess(boolean hasDataToProcess) {
    this.hasDataToProcess = hasDataToProcess;
  }

  public static void main(String[] args) {
    //同一个对象
    final MySignal1 my = new MySignal1();
    //线程1设置hasDataToProcess值为true
    final Thread t1 = new Thread(new Runnable() {
      @Override
      public void run() {
        my.setHasDataToProcess(true);
      }
    });
    t1.start();
    //线程2取这个值hasDataToProcess
    Thread t2 = new Thread(new Runnable() {
      @Override
      public void run() {
        try {
          //等待线程1完成后取值
          t1.join();
        } catch (InterruptedException e) {
          e.printStackTrace();
        }
        my.getHasDataProcess();
        System.out.println("t1改变以后的值:"+my.getHasDataProcess());
      }
    });
    t2.start();
  }
}

运行结果如下:

t1改变以后的值:true

2、等待/唤醒(wait/notify)机制

以资源为例,生产者生产一个资源,通知消费者就消费掉一个资源,生产者继续生产资源,消费者消费资源,以此循环,代码如下。

import sun.security.util.Password;

//资源类
class Resource {
  private String name;
  private int count = 1;
  private boolean flag = false;

  public synchronized void set(String name) {
    //生产资源
    while (flag) {
      try {
        //线程等待
        wait();
      } catch (InterruptedException e) {
      }
    }
    this.name = name + "----" + count + "+++++";
    System.out.println(Thread.currentThread().getName() + "..生产者..." + this.name);
    flag = true;
    //唤醒等待中的消费者
    this.notifyAll();
  }

  public synchronized void out() {
    //消费资源
    while (!flag) {
      try {
        //线程等待,生产者生产资源
        wait();
      } catch (InterruptedException e) {
      }
    }
    System.out.println(Thread.currentThread().getName() + "...消费者..." + this.name);
    flag = false;
    //唤醒消费者,生产资源
    this.notifyAll();
  }
}

//生产者
class Producer implements Runnable {
  private Resource rs;

  public Producer(Resource rs) {
    this.rs = rs;
  }

  //生产者生产资源
  @Override
  public void run() {
    while (true) {
      rs.set("商品");
    }
  }
}

//消费者消费资源
class Consumer implements Runnable {
  private Resource rs;

  public Consumer(Resource rs) {
    this.rs = rs;
  }

  //消费者消费资源
  @Override
  public void run() {
    while (true) {
      rs.out();
    }
  }
}

public class ProducerConsumerDemo {
  public static void main(String[] args) {
    Resource r = new Resource();
    Producer p = new Producer(r);
    Consumer c = new Consumer(r);
    Thread t1 = new Thread(p);
    Thread t2 = new Thread(c);
    t1.start();
    t2.start();
  }
}

运行结果如下:

Thread-0..生产者...商品----1+++++
Thread-1...消费者...商品----1+++++
Thread-0..生产者...商品----1+++++
Thread-1...消费者...商品----1+++++
Thread-0..生产者...商品----1+++++
Thread-1...消费者...商品----1+++++
Thread-0..生产者...商品----1+++++

以上就是本文的全部内容,希望对大家的学习有所帮助,也希望大家多多支持脚本之家。

相关文章

  • SpringBoot 之启动流程详解

    SpringBoot 之启动流程详解

    SpringBoot 是一个基于 Spring 框架的快速开发框架,旨在简化 Spring 应用程序的开发和部署。在本文中,我们将深入分析 SpringBoot 启动过程的源代码,并提供必要的解释和说明
    2023-04-04
  • Java实现手写线程池实例并测试详解

    Java实现手写线程池实例并测试详解

    这篇文章主要来模拟一下线程池和工作队列的流程,以及编写代码和测试类进行测试。文中的示例代码讲解详细,感兴趣的小伙伴可以了解一下
    2023-02-02
  • Jmeter测试必知的名词及环境搭建

    Jmeter测试必知的名词及环境搭建

    我们本章开始学习Jmeter,后续还会有RF以及LoadRunner 的介绍,为什么要学习Jmeter,它主要是用来做性能测试的,其中它也需要间接或直接的需要用到抓包工具
    2021-09-09
  • spring中的DI步骤详解

    spring中的DI步骤详解

    本文主要介绍了bean的装配实现过程,通常对于简单数据类型数据初始主要在获得对象后,使用setter方法完成,所谓的装配主要是复杂数据类型的依赖注入,感兴趣的朋友一起看看吧
    2023-11-11
  • Java初级必看的数据类型与常量变量知识点

    Java初级必看的数据类型与常量变量知识点

    这篇文章主要给大家介绍了关于Java初级必看的数据类型与常量变量知识点的相关资料,需要的朋友可以参考下
    2023-11-11
  • Java探索之Hibernate主键生成策略详细介绍

    Java探索之Hibernate主键生成策略详细介绍

    这篇文章主要介绍了Java探索之Hibernate主键生成策略详细介绍,具有一定参考价值,需要的朋友可以了解下。
    2017-10-10
  • Java给JFrame窗口设置热键的方法实现

    Java给JFrame窗口设置热键的方法实现

    这篇文章主要介绍了Java给JFrame窗口设置热键的方法实现,文中通过示例代码以及图文介绍的非常详细,对大家的学习或者工作具有一定的参考学习价值,需要的朋友们下面来一起学习学习吧
    2020-07-07
  • 一文带你搞懂Java中i++ 和 ++i的区别

    一文带你搞懂Java中i++ 和 ++i的区别

    在Java中,i++和++i都用于递增变量i的值,但它们之间有一个细微的区别,i++是后缀递增操作符,++i是前缀递增操作符,在大多数情况下,这两种递增操作的结果都是一样的,但在某些特定的表达式和逻辑中,它们可能会产生不同的效果,本文将带大家搞清Java中i++ 和 ++i的区别
    2023-09-09
  • 浅谈maven 多环境打包发布的两种方式

    浅谈maven 多环境打包发布的两种方式

    这篇文章主要介绍了浅谈maven 多环境打包发布的两种方式,小编觉得挺不错的,现在分享给大家,也给大家做个参考。一起跟随小编过来看看吧
    2018-08-08
  • 基于springboot实现redis分布式锁的方法

    基于springboot实现redis分布式锁的方法

    这篇文章主要介绍了基于springboot实现redis分布式锁的方法,文中通过示例代码介绍的非常详细,对大家的学习或者工作具有一定的参考学习价值,需要的朋友们下面随着小编来一起学习学习吧
    2020-11-11

最新评论