AtomicInteger。一个提供原子操作的Integer的类。

在Java语言中,++i和i++操作并非线程安全的。在使用的时候,不可避免的会用到synchronized关键字。

而AtomicInteger则通过一种线程安全的加减操作接口。

样例:Java代码:

CashierContext类部分代码:  

private Map<String, AtomicInteger> counter          = new HashMap<String, AtomicInteger>();  

private void initCounter() {
counter.put("cvm", new AtomicInteger(0));
} //被调用一次自己主动+1 public MobileCashierViewModel getCvm() { if (cvm != null) {
counter.get("cvm").incrementAndGet();
}
return cvm;
}

使用场景:

由于通过WS服务获取MobileCashierViewModel 这个对象比較频繁,会非常影响系统资源。能够将cvm存入缓存中,想要查看缓存cvm有多大价值,那么能够设置一个计数,来统记cvm被调用的次数

然后将CashierContext放入ThreadLocal中,然后再写一个过滤器,在过滤器里面能够得到获取这个服务从缓存中取的次数,这个就能够非常easy看出来缓存价值。

那么为什么不使用记数器自加呢,比如count++这种,由于这种计数是线程不安全的。高并发訪问时统计会有误,而AtomicInteger为什么能够达到多而不乱。处理高并发应付自如呢,我们才看看AtomicInteger的源码:

Java代码

private volatile int value;  

大家能够看到有这个变量,value就是你设置的自加起始值。注意看它的訪问控制符。是volatile,这个就是保证AtomicInteger线程安全的根源,熟悉并发的同学一定知道在java中处理并发主要有两种方式:

1。synchronized关键字。这个大家应当都各种面试和笔试中常常遇到。

2。volatile修饰符的使用。相信这个修饰符大家平时在项目中使用的也不是非常多。

这里重点说一下volatile:

Volatile修饰的成员变量在每次被线程訪问时,都强迫从共享内存又一次读取该成员的值,并且。当成员变量值发生变化时,强迫将变化的值又一次写入共享内存。这样两个不同的线程在訪问同一个共享变量的值时,始终看到的是同一个值。

java语言规范指出:为了获取最佳的执行速度,同意线程保留共享变量的副本,当这个线程进入或者离开同步代码块时。才与共享成员变量进行比对,假设有变化再更新共享成员变量。

这样当多个线程同一时候訪问一个共享变量时。可能会存在值不同步的现象。

而volatile这个值的作用就是告诉VM:对于这个成员变量不能保存它的副本,要直接与共享成员变量交互。

建议:当多个线程同一时候訪问一个共享变量时,能够使用volatile。而当訪问的变量已在synchronized代码块中时,不必使用。

缺点:使用volatile将使得VM优化失去作用,导致效率较低。所以要在必要的时候使用。

引用自:

http://haininghacker-foxmail-com.iteye.com/blog/1401346

AtomicInteger在实际项目中的应用的更多相关文章

  1. 项目中遇到的死锁问题: Lock wait timeout exceeded; try restarting transaction

    最近项目中频繁出现  Lock wait timeout exceeded; try restarting transaction这个错误,把我们弄得痛苦不堪啊,为了解决问题,上网上找好多资料,终于把 ...

  2. SSH 项目中 使用websocket 实现网页聊天功能

    参考文章  :java使用websocket,并且获取HttpSession,源码分析    http://www.cnblogs.com/zhuxiaojie/p/6238826.html 1.在项 ...

  3. VS项目中使用Nuget还原包后编译生产还一直报错?

    Nuget官网下载Nuget项目包的命令地址:https://www.nuget.org/packages 今天就遇到一个比较奇葩的问题,折腾了很久终于搞定了: 问题是这样的:我的解决方案原本是好好的 ...

  4. ABP项目中使用Swagger生成动态WebAPI

    本文是根据角落的白板报的<使用ABP实现SwaggerUI,生成动态webapi>一文的学习总结,感谢原文作者角落的白板报. 1 安装Swashbuckle.core 1.1 选择WebA ...

  5. iOS 之项目中遇到的问题总结

    昨天去一家公司面试,面试官问了我在项目开发中遇到过哪些问题,是什么引起的,怎样解决的? 当时由于有点小紧张只说出了一两点,现在就来好好总结一下. 问题: 1.两表联动 所谓的两表联动就是有左右两个表格 ...

  6. My97DatePicker时间控件在项目中的应用

    一.下载My97DatePicker的压缩包My97DatePicker.rar,解压. 注:My97DatePicker最新版本有开发包,项目中使用时删掉,以便节省空间,提高程序的运行效率. 二.在 ...

  7. 在项目中同时使用Objective-C和Swift

    苹果发布的Swift语言可以和之前的Objective-C语言同时存在于一个项目中. 可能有人会认为是同一个类文件中既可以有Objective-C也可以有Swift,这是不对的.同一个类文件或同一个代 ...

  8. 在数据库访问项目中使用微软企业库Enterprise Library,实现多种数据库的支持

    在我们开发很多项目中,数据访问都是必不可少的,有的需要访问Oracle.SQLServer.Mysql这些常规的数据库,也有可能访问SQLite.Access,或者一些我们可能不常用的PostgreS ...

  9. 在基于MVC的Web项目中使用Web API和直接连接两种方式混合式接入

    在我之前介绍的混合式开发框架中,其界面是基于Winform的实现方式,后台使用Web API.WCF服务以及直接连接数据库的几种方式混合式接入,在Web项目中我们也可以采用这种方式实现混合式的接入方式 ...

随机推荐

  1. 备忘 CSS字体中英文名称对照表

    转载自:http://www.jb51.net/css/67658.html 在CSS文件中,我们常看到有些字体名称变成了乱码,这是由于编写者将中文字体的名字直接写成了中文,并且再上传或者拷贝复制的时 ...

  2. php中 ob_start()有什么作用

    <?php ob_start(); //开启缓冲区 echo "这是第一次输出内容!\n"; $ff[1] = ob_get_contents() ; //获取当前缓冲区内容 ...

  3. wampSever的mysql操作

    单击wampserver图标,选择mysql console 输入密码 123qwe,root用户默认密码为空 mysql客户端管理工具使用wampserver自带的phpmyadmin

  4. bzoj 2794 [Poi2012]Cloakroom 离线+背包

    题目大意 有n件物品,每件物品有三个属性a[i], b[i], c[i] (a[i]<b[i]). 再给出q个询问,每个询问由非负整数m, k, s组成,问是否能够选出某些物品使得: 对于每个选 ...

  5. 【BZOJ2243】染色(树链剖分)

    题意: 给定一棵有n个节点的无根树和m个操作,操作有2类: 1.将节点a到节点b路径上所有点都染成颜色c: 2.询问节点a到节点b路径上的颜色段数量(连续相同颜色被认为是同一段),如“112221”由 ...

  6. Error querying database找不到数据库的错误可能发生的原因..

    这个问题纠结了大概两个小时.原因是这样的,我刚刚换了一台新的电脑,准备把以前电脑上自己搭建的小项目放到新电脑上面,用myeclipse引入项目之后,启动项目在浏览器跑起来.然后输入账号密码登录主页,报 ...

  7. 10个JavaScript难点--摘抄

    1. 立即执行函数 立即执行函数,即Immediately Invoked Function Expression (IIFE),正如它的名字,就是创建函数的同时立即执行.它没有绑定任何事件,也无需等 ...

  8. Yii createCommand CURD操作

    本文用作工作记录,也许有人会问为什么不用 Yii 的 Model 去操作 DB,原因很简单,Yii 的 Model 写法上是方便了很多,但是会执行多余的 SQL,打开 Yii 的执行 log 就会发现 ...

  9. UPC 2219: A^X mod P

    题形:另类快速幂 题意: f(x) = K, x = 1 f(x) = (a*f(x-1) + b)%m , x > 1 Now, Your task is to calculate ( A^( ...

  10. Oracle For 循环添加数据

    自己亲自使用的,绝对OK --添加数据declare i number; --用for实现 begin for i in 0 .. 500 loop insert into cust(custsn,t ...