zoukankan      html  css  js  c++  java
  • 并发库应用之二 & Java原子性操作类应用

      Java5的线程并发库中,提供了一组atomic class来帮助我们简化同步处理。基本工作原理是使用了同步synchronized的方法实现了对一个long, integer, 对象的增、减、赋值(更新)操作

           java.util.concurrent在并发编程中很常用的实用工具类。

                         |----locks为锁和等待条件提供一个框架的接口和类,它不同于内置同步和监视器

                         |----atomic类的小工具包,支持在单个变量上解除锁的线程安全编程。可以对基本类型、数组中的基本类型、类中的基本类型等进行操作

                                |----AtomicInteger  用于提供整型数字原子性操作

               |----AtomicIntegerArray  用于提供整型数组原子性操作

               |----AtomicIntegerFieldUpdater  用于提供类对象中的整型数据原子性操作

               ......  对应有Double...相类似的原子性操作类

      以上原子性操作类具体如何使用详情可以查看相应的官方jdk文档,下面通过简单的两个例子的对比来看一下 AtomicInteger 的强大的功能,分别是普通的方法与使用AtomicInteger类的方法:

    普通方法实现方案:

     1 public class CommonTest {
     2     private volatile int count = 0; //volatile关键字实现线程间数据共享
     3 
     4     public synchronized void increment() {
     5        count++; //若要线程安全执行,需要加锁
     6     }
     7 
     8     public int getCount() {
     9         return count;
    10     }
    11 }

    使用AtomicInteger类的方法实现

     1 public class AtomicIntegerTest {
     2     private AtomicInteger count = new AtomicInteger();
     3 
     4     public synchronized void increment() {
     5         count.incrementAndGet();
     6     }
     7 
     8     public int getCount() {
     9         return count.get();
    10     }
    11 }

    调用两个类的主方法实现

     1 public class MainClass {    
     2     public static void main(String[] args) {
     3         //final CommonTest atomicIntegerTest = new CommonTest();
     4         final AtomicIntegerTest atomicIntegerTest = new AtomicIntegerTestTrue();
     5         for (int j = 0; j < 3; j++) { //各自同时开启3个线程
     6             //增加线程
     7             new Thread(new Runnable() {
     8                 @Override
     9                 public void run() {
    10                     for (int i = 0; i < 10; i++) {
    11                         atomicIntegerTest.increment();
    12                         try {
    13                             Thread.sleep(1000);
    14                         } catch (InterruptedException e) {
    15                             e.printStackTrace();
    16                         }
    17                     }
    18                 }
    19             }).start();
    20             //读取线程
    21             new Thread(new Runnable() {
    22                 @Override
    23                 public void run() {
    24                     for (int i = 0; i < 10; i++) {
    25                         System.out.println(Thread.currentThread().getName() + "-->" + atomicIntegerTest.getCount());
    26                         try {
    27                             Thread.sleep(1000);
    28                         } catch (InterruptedException e) {
    29                             e.printStackTrace();
    30                         }
    31                     }
    32                 }
    33             }).start();
    34         }
    35     }
    36 }

    运行结果如下所示:

    Thread-1-->1
    Thread-3-->2
    Thread-5-->3
    Thread-3-->4
    Thread-1-->5
    Thread-5-->5
    Thread-1-->9
    Thread-5-->9
    Thread-3-->9
    Thread-5-->12
    Thread-3-->12
    Thread-1-->12
    Thread-3-->13
    Thread-1-->13
    Thread-5-->14
    Thread-5-->16
    Thread-1-->16
    Thread-3-->16
    Thread-1-->21
    Thread-3-->21
    Thread-5-->21
    Thread-5-->22
    Thread-1-->22
    Thread-3-->22
    Thread-1-->25
    Thread-5-->25
    Thread-3-->25
    Thread-3-->29
    Thread-1-->30
    Thread-5-->29
    

      从上面的例子中我们可以看出:使用AtomicInteger是非常的安全的

      那么为什么不使用记数器自加呢,例如count++这样的,因为这种计数是线程不安全的,高并发访问时统计会有误,而AtomicInteger为什么能够达到多而不乱,处理高并发应付自如呢?

      这是由硬件提供原子操作指令实现的。在非激烈竞争的情况下,开销更小,速度更快。

    提示:常用基本类的原子操作讲解完毕,接下来我们就开始进入有关多线程线程池相关概念讲解,具体详情请查看我的下一篇博客:并发库应用之三 & 线程池与定时器应用

  • 相关阅读:
    npm 全局执行 update 、 outdated 出现 npm-debug.log 404 错误的问题
    python 爬虫爬取内容时, xa0 、 u3000 的含义
    SCNU ACM 2016新生赛决赛 解题报告
    SCNU ACM 2016新生赛初赛 解题报告
    【记录】Ubuntu下安装VirtualBox
    Ubuntu16.04 LTS下apt安装WireShark
    Java的初始化块、静态初始化块、构造函数的执行顺序及用途探究
    Ubuntu在wps-office等qt5程序下不能切换中文fcitx输入法的问题
    Ubuntu管理开机启动服务项 -- 图形界面的Boot-up Manager
    解决Ubuntu下Firefox+OpenJDK没有Java插件的问题
  • 原文地址:https://www.cnblogs.com/liang1101/p/6517486.html
Copyright © 2011-2022 走看看