多线程1:AtomicInteger的使用,多线程叠加或叠减
- import java.util.concurrent.atomic.AtomicInteger;
- public class AtomicIntegerTest {
- public AtomicInteger inc = new AtomicInteger();
- public void increase() {
- inc.getAndIncrement();//i++操作
- //inc.getAndDecrement();//i--操作
- }
- public static void main(String[] args) {
- final AtomicIntegerTest test = new AtomicIntegerTest();
- for (int i = 0; i < 10; i++) {
- new Thread() {
- public void run() {
- for (int j = 0; j < 1000; j++)
- test.increase();
- };
- }.start();
- }
- while (Thread.activeCount() > 1)
- // 保证前面的线程都执行完
- Thread.yield();
- System.out.println(test.inc);
- }
- }
可以发现结果都是10000,也就是说AtomicInteger是线程安全的。
值得一看。
这里,我们来看看AtomicInteger是如何使用非阻塞算法来实现并发控制的。
AtomicInteger的关键域只有一下3个:
- // setup to use Unsafe.compareAndSwapInt for updates
- private static final Unsafe unsafe = Unsafe.getUnsafe();
- private static final long valueOffset;
- private volatile int value;
这里, unsafe是Java提供的获得对对象内存地址访问的类,注释已经清楚的写出了,它的作用就是在更新操作时提供“比较并替换”的作用。实际上就是AtomicInteger中的一个工具。
valueOffset是用来记录value本身在内存的便宜地址的,这个记录,也主要是为了在更新操作在内存中找到value的位置,方便比较。
注意:value是用来存储整数的时间变量,这里被声明为volatile,就是为了保证在更新操作时,当前线程可以拿到value最新的值(并发环境下,value可能已经被其他线程更新了)。
这里,我们以自增的代码为例,可以看到这个并发控制的核心算法:
- /**
- * Atomically increments by one the current value.
- *
- * @return the updated value
- */
- public final int incrementAndGet() {
- for (;;) {
- //这里可以拿到value的最新值
- int current = get();
- int next = current + 1;
- if (compareAndSet(current, next))
- return next;
- }
- }
- public final boolean compareAndSet(int expect, int update) {
- //使用unsafe的native方法,实现高效的硬件级别CAS
- return unsafe.compareAndSwapInt(this, valueOffset, expect, update);
- }
好了,看到这个代码,基本上就看到这个类的核心了。相对来说,其实这个类还是比较简单的。可以参考http://hittyt.iteye.com/blog/1130990
多线程1:AtomicInteger的使用,多线程叠加或叠减相关推荐
- 5天玩转C#并行和多线程编程 —— 第五天 多线程编程大总结
5天玩转C#并行和多线程编程 -- 第五天 多线程编程大总结 5天玩转C#并行和多线程编程系列文章目录 5天玩转C#并行和多线程编程 -- 第一天 认识Parallel 5天玩转C#并行和多线程编程 ...
- java第七章多线程_第七章 多线程
7 多线程 7.1 进程和线程 1.进程进程是一个正在执行中的程序 每一个进程都有一个执行顺序,该顺序是一个执行路径,或者叫做一个控制单元 2.线程线程就是进程中的一个独立控制单元 线程在控制着进程的 ...
- 秒杀多线程第十六篇 多线程十大经典案例之一 双线程读写队列数据
本文配套程序下载地址为:http://download.csdn.net/detail/morewindows/5136035 转载请标明出处,原文地址:http://blog.csdn.net/mo ...
- java多线程的实现方式_Java 多线程(一)——多线程的实现方式
一.前言 Java 异常的处理方式与自定义异常 我们已经讲完了,从今天开始我们来学习多线程. 二.与多线程相关的概念 2.1.并发与并行并发:指两个或多个事件在同一个时间段内发生,具体如下图所示: 并 ...
- VS中的多线程(/MT)、多线程调试(/MTd)、多线程DLL(/MD)、多线程调试DLL(/MDd)的区别(转载)
转载链接https://blog.csdn.net/qq_33757398/article/details/82156956 一种语言的开发环境往往会附带有语言库,这些库就是对操作系统的API的包装, ...
- java多线程采集+线程同步-【多线程数据采集之四】
前些日子讲解了java数据抓取, 今天就讲解最核心的. java多线程数据抓取. java多线程采集+数据同步+线程同步[多线程数据采集之四] 主要讲解多线程抓取,多线程同步,多线程启动,控制等操作. ...
- 多线程编程(1): python对多线程的支持
python多线程编程(1): python对多线程的支持 前面介绍过多线程的基本概念,理解了这些基本概念,掌握python多线程编程就比较容易了. 在开始之前,首先要了解一下python对多线程的支 ...
- .NET异步和多线程系列(四)- 多线程异常处理、线程取消、多线程的临时变量问题、线程安全和锁lock
本文是.NET异步和多线程系列第四章,主要介绍的是多线程异常处理.线程取消.多线程的临时变量问题.线程安全和锁lock等. 一.多线程异常处理 多线程里面抛出的异常,会终结当前线程,但是不会影响别的线 ...
- 易语言 mysql多线程_易语言数据库多线程 易语言数据库教程
为什么易语言两个线程同时对一个MYSQL数据? 数据库有自己的连接锁定机制.如果同一台机器使用同一接口插入,则多线程和单线程是相同的. 除非您有多个数据库服务器,然后使用多线程来完成上述工作,否则效率 ...
最新文章
- studio添加依赖工程方法
- 和计算机互动英语,计算机专业英语互动教学方法探讨
- ValueError: Program dot not found in path.python下运行pygraphviz出现报错
- 王昶衡(帮别人名字作诗)
- 解决JupyterLab/JupyterNotebook安装pycherts后依旧报错报错 ModuleNotFoundError: No module named ‘pyecharts‘
- 达梦数据库如何连接MySQL_如何创建达梦数据库
- 低延时互动直播双十一优惠活动
- pymongo使用经验
- 子界类型(Subrange types)
- 产品读书《定位:有史以来对美国营销影响最大的观念》
- 如何做一个简单的学生喜欢家长买单的scratch小游戏
- 非支配快速排序算法详解
- adaway的jni设计摸索
- STM32调试过程 常见错误及解决方案
- 又一大的技术站点域名被ClientHold了
- win10禁用操作系统的服务器,win10服务哪些可以禁止启动 win10哪些服务可以关闭禁用...
- ubuntu安装和使用labellmg(含pyqt4的安装教程)
- 解决浏览器连不上校园网问题
- STM32103驱动28BYJ48步进电机
- GoogleNet、AleXNet、VGGNet、ResNet等总结
热门文章
- 《FlaskWeb开发:基于Python的Web应用开发实战》笔记
- 汇编语言 LOOP和[BX]的联合应用
- php如何获取ajax请求,php-从ajax调用获取json数据
- mysql重新载入my.cnf_怎么重新加载MySQL的my.cnf?
- Spring学习-- SpEL表达式
- 记一次 @Transactional不生效的问题
- JAXB 有两个名为 ** 的属性,类的两个属性具有相同名称 **解决方案
- leetcode -- 357. Count Numbers with Unique Digits
- 洛谷——P1071 潜伏者
- 未公开接口主要指以下哪几类_Java8的 Stream 函数式接口,你了解多少?