在多线程访问共享对象和数据时候大致可以分为两大类。

1:如果每个线程执行的代码相同,可以使用同一个runnable对象,这个runnable对象中有那个共享对象。如:买票系统。

public class MulteThreadlShareData {public static void main(String[] args) {ShareData shareData = new ShareData();new Thread(shareData).start();new Thread(shareData).start();}static class ShareData implements Runnable{int count = 100;@Overridepublic void run() {while(count>0){decrease();}}public synchronized void decrease(){count--;System.out.println(Thread.currentThread().getName()+"this count: "+count);}}
}

2:如果每个线程执行的代码不相同,就要用不同的runnable对象了。这种方式又有两种来实现这些runnable对象之间的数据共享。

  •   将共享数据封装在另一个对象中,然后将这个对象逐一传递给各个runnable对象中。每个线程共享数据的操作方法也分配到了这个对象身上去完成,这样容易实现针对该数据进行共享数据的互斥和通信。代码实现如下:

    public class MulteThreadlShareData2 {public static void main(String[] args) {final ShareData shareData = new ShareData();new Thread(new Decrease(shareData)).start();new Thread(new Increment(shareData)).start();}static class Decrease implements Runnable{private ShareData shareData;public Decrease(ShareData shareData){this.shareData=shareData;}@Overridepublic void run() {shareData.decrease();}}static class Increment implements Runnable{private ShareData shareData;public Increment(ShareData shareData){this.shareData=shareData;}@Overridepublic void run() {shareData.increment();}}static class ShareData{int count = 100;public synchronized void decrease(){count--;System.out.println(Thread.currentThread().getName()+"decrease this count: "+count);}public synchronized void increment(){count++;System.out.println(Thread.currentThread().getName()+"increment this count: "+count);}}
    }
  •   将这些runnable对象作为某个类的内部类,共享数据作为这个外部类的成员变量,每个线程对共享数据的操作也分配到外部类,以便实现对共享数据进行的各个操作进行互斥和通信,作为内部类的各个runnable对象调用外部类的这些方法。
    public class MulteThreadlShareData3 {static int count = 100;public static void main(String[] args) {new Thread(new Decrease()).start();new Thread(new Increment()).start();}public synchronized static void decrease(){count--;System.out.println(Thread.currentThread().getName()+"decrease this count: "+count);}public synchronized static void increment(){count++;System.out.println(Thread.currentThread().getName()+"increment this count: "+count);}static class Decrease implements Runnable{@Overridepublic void run() {decrease();}}static class Increment implements Runnable{@Overridepublic void run() {increment();}}
    }
  •   上面两种方式的结合:将共享数据封装到另一个对象中,各个线程对共享数据操作的方法也分配到那个对象上去完成,对象作为外部类的成员变量或方法的局部变量,每个runnable对象作为外部类中的成员内部类或局部内部类。
    public class MulteThreadlShareData1 {public static void main(String[] args) {final ShareData shareData = new ShareData();new Thread(new Runnable() {@Overridepublic void run() {while(true){shareData.decrease();}    }}).start();new Thread(new Runnable() {@Overridepublic void run() {while(true){shareData.increment();}}}).start();}static class ShareData{int count = 100;public synchronized void decrease(){count--;System.out.println(Thread.currentThread().getName()+"this count: "+count);}public synchronized void increment(){count++;System.out.println(Thread.currentThread().getName()+"this count: "+count);}}
    }

总之:要同步和互斥的几段代码最好放在几个独立的方法中,这些方法在放在同一个类中,这样容易实现他们之间的同步互斥和通信。

多线程访问共享对象和数据的方式相关推荐

  1. 多个线程访问共享对象和数据的方式

    1.如果每个线程执行的代码相同,可以使用同一个Runnable对象,这个Runnable对象中有那个共享数据,例如,卖票系统就可以那么做. 2.如果每个线程执行的代码不同,这时候就需要用不同的Runn ...

  2. linux多线程访问共享资源,多个线程访问共享对象和数据

    多个线程访问共享对象和数据有很多方式,但是可以分为两大类:1.多线程执行代码相同的.2.多线程执行代码不同的 对于多线程执行代码相同的情况来说: 1)使用同一个Runnable对象,在new Thre ...

  3. C++智能指针的多线程访问共享对象问题以及自定义删除器

    多线程访问共享对象问题 问题描述:线程A和线程B访问一个共享的对象,如果线程A正在析构这个对象的时候,线程B又要调用该共享对象的成员方法,此时可能线程A已经把对象析构完了,线程B再去访问该对象,就会发 ...

  4. java 多线程 共享数据_JAVA多线程提高四:多个线程之间共享数据的方式

    多个线程访问共享对象和数据的方式 如果每个线程执行的代码相同,可以使用同一个Runnable对象,这个Runnable对象中有那个共享数据,例如,买票系统就可以这么做. 如果每个线程执行的代码不同,这 ...

  5. Java shared data_Java多个线程之间处理共享数据的方式

    题目要求: 有4个线程,其中两个线程每次对x加1,另外两个每次对x减1,如何实现? 分析: x就是这4个线程要处理的共享数据,不同种线程有不同的处理方式,但操作的数据是共同的,联想到"窗口买 ...

  6. 多线程訪问共享数据(1)

    多线程訪问共享数据解决方式: 一.什么是多线程 线程是程序中一个单一的顺序控制流程.在单个程序中同一时候运行多个线程完毕不同的工作,称为多线程. 全部的线程尽管在微观上是串行运行的,可是在宏观上你全然 ...

  7. js给数组添加数据的方式/js 向数组对象中添加属性和属性值

    参考:https://www.cnblogs.com/ayaa/p/14732349.html js给数组添加数据的方式有以下几种: 直接利用数组下标赋值来增加(数组的下标起始值是0) 例,先存在一个 ...

  8. map容器对象插入数据的4种方式讲解

    map容器对象插入数据的4种方式讲解 map容器对象插入数据的4种方式 #include <string> #include <iostream>  #include < ...

  9. Vue 对象和数据的强制更新方式

    对象和数据的强制更新 数组更新 以下支持自动更新 push() //向后添加     pop() //删除最后一个     shift() //删除第一个     unshift() //向第一个添加 ...

最新文章

  1. MySQL中的常见子查询语句
  2. 关于Redis的使用!
  3. python五十:反射
  4. 基于文本挖掘的企业隐患排查质量分析模型
  5. ASP技巧实例:几行代码解决防止表单重复提交
  6. 计算机蠕虫的存在形式,计算机蠕虫
  7. spark中flatMap函数用法
  8. 全文检索技术_中药图片拍照识别系统,爬虫、深度学习技术android app 源码分享...
  9. Mysql 零距离-入门(二)
  10. linux ftp 警告暗号话,ssh,FTP到远程服务器时,显示自定义的警告信息
  11. Spring-core-ClassUtils类
  12. Entity Framework Codefirst的配置步骤
  13. mysql数据库不存在_mysql 数据库不存在
  14. Redis的持久化 RDB AOF
  15. [转]中国著名黑客你知道多少?
  16. 通过web前端实现水印制作
  17. 表格中复制后出现空格_尝过廉江这个美食后,已经连续3天出现在下午茶名单中!...
  18. J2EE平台WEB组件开发中如何使用定制标签
  19. VMware:速修复这三个严重的 Workspace ONE Assist 软件漏洞
  20. .net使用Easyui+MVC进行图片上传的实现

热门文章

  1. vmtouch--the Virtual Memory Toucher
  2. RabbitMQ官方中文入门教程(PHP版) 第三部分:发布/订阅(Publish/Subscribe)
  3. C++ Primer Plus(十一)—— 使用类
  4. POST 变为AJAX提交代码。
  5. Java Date 日期 时间 相关方法
  6. ucos内存管理笔记
  7. Matlab Simulink如何生成谐波
  8. ffmpeg学习1 音视频基本概念
  9. caffe学习(三):caffe开发环境安装(Ubuntu)
  10. 数据类型_分享redis中除5种基础数据类型以外的高级数据类型