JAVA高级:多核线程-volatile原理与技巧

为什么使用volatile比同步代价更低?

同步的代价, 主要由其覆盖范围决定, 如果可以降低同步的覆盖范围, 则可以大幅提升程序性能.

而volatile的覆盖范围仅仅变量级别的. 因此它的同步代价很低.

volatile原理是什么?

volatile的语义, 其实是告诉处理器, 不要将我放入工作内存, 请直接在主存操作我.(工作内存详见java内存模型)

因此, 当多核或多线程在访问该变量时, 都将直接操作主存, 这从本质上, 做到了变量共享.

volatile的有什么优势?

1, 更大的程序吞吐量

2, 更少的代码实现多线程

3, 程序的伸缩性较好

4, 比较好理解, 无需太高的学习成本

volatile有什么劣势?

1, 容易出问题

2, 比较难设计

volatile运算存在脏数据问题

volatile仅仅能保证变量可见性, 无法保证原子性.

volatile的race condition示例:

public class TestRaceCondition {
private volatile int i = 0;
public void increase() {
i++;
}
public int getValue() {
return i;
}
}

当多线程执行increase方法时, 是否能保证它的值会是线性递增的呢?

答案是否定的.

原因:

这里的increase方法, 执行的操作是i++, 即 i = i + 1;

针对i = i + 1, 在多线程中的运算, 本身需要改变i的值.

如果, 在i已从内存中取到最新值, 但未与1进行运算, 此时其他线程已数次将运算结果赋值给i.

则当前线程结束时, 之前的数次运算结果都将被覆盖.

即, 执行100次increase, 可能结果是 < 100.

一般来说, 这种情况需要较高的压力与并发情况下, 才会出现.

时间: 2024-11-02 11:27:40

JAVA高级:多核线程-volatile原理与技巧的相关文章

《Java线程与并发编程实践》—— 1.2 操作更高级的线程任务

1.2 操作更高级的线程任务 之前的线程任务都和如何配置一个线程对象以及启动关联的线程相关.不过,Thread类也能支持更多高级的任务,包括中断其他线程.将线程join到另一条线程中以及致使线程睡眠. 1.2.1 中断线程 Thread类提供了一种线程可以中断其他线程的机制.当一个线程被中断时,它会抛出java.lang.InterruptedException.这一机制由下面的3种方法构成. void interrupt():中断调用此方法的Thread对象所关联的线程.当一条线程由于调用了T

转 Java并发编程:volatile关键字解析

volatile这个关键字可能很多朋友都听说过,或许也都用过.在Java  5之前,它是一个备受争议的关键字,因为在程序中使用它往往会导致出人意料的结果.在Java 5之后,volatile关键字才得以重获生机. volatile关键字虽然从字面上理解起来比较简单,但是要用好不是一件容易的事情.由于volatile关键字是与Java的内存模型有关的,因此在讲述volatile关键之前,我们先来了解一下与内存模型相关的概念和知识,然后分析了volatile关键字的实现原理,最后给出了几个使用vol

Java并发编程:volatile关键字详细解析_java

volatile这个关键字可能很多朋友都听说过,或许也都用过.在Java 5之前,它是一个备受争议的关键字,因为在程序中使用它往往会导致出人意料的结果.在Java 5之后,volatile关键字才得以重获生机. volatile关键字虽然从字面上理解起来比较简单,但是要用好不是一件容易的事情.由于volatile关键字是与Java的内存模型有关的,因此在讲述volatile关键之前,我们先来了解一下与内存模型相关的概念和知识,然后分析了volatile关键字的实现原理,最后给出了几个使用vola

Java并发编程之volatile关键字解析

原文出处海子 一内存模型的相关概念 二并发编程中的三个概念 三Java内存模型 四深入剖析volatile关键字 五使用volatile关键字的场景 volatile这个关键字可能很多朋友都听说过,或许也都用过.在Java 5之前,它是一个备受争议的关键字,因为在程序中使用它往往会导致出人意料的结果.在Java 5之后,volatile关键字才得以重获生机. volatile关键字虽然从字面上理解起来比较简单,但是要用好不是一件容易的事情.由于volatile关键字是与Java的内存模型有关的,

Java高级软件工程师面试考纲

当前,市面上有<Java XX宝典>类似的图书,而且图书中的内容都着重在讲解Java最为基础的部分,最严重的是,里面有着大量错误的内容,极具误导性.另外,网上也有各种各样的Java面试题, 很多也是着重在Java语言基础上.实际上,如果要应聘高级开发工程师职务,仅仅懂得Java的基础知识是远远不够的,还必须懂得常用数据结构.算法.网 络.操作系统等知识.因此本文不会讲解具体的技术,笔者综合自己应聘各大公司的经历,整理了一份大公司对Java高级开发工程师职位的考核纲要,希望可以帮助到需要的人.

ava实现线程池原理:适用于电商网站之类的交互频繁的网站

线程池是一种多线程处理形式,处理过程中将任务添加到队列,然后在创建线程后自动启动这些任务.线程池线程都是后台线程.每个线程都使用默认的堆栈大小,以默认的优先级运行,并处于多线程单元中.如果某个线程在托管代码中空闲(如正在等待某个事件),则线程池将插入另一个辅助线程来使所有处理器保持繁忙.如果所有线程池线程都始终保持繁忙,但队列中包含挂起的工作,则线程池将在一段时间后创建另一个辅助线程但线程的数目永远不会超过最大值.超过最大值的线程可以排队,但他们要等到其他线程完成后才启动. 组成部分 1.线程池

new Thread的弊端及Java四种线程池的使用

介绍new Thread的弊端及Java四种线程池的使用,对Android同样适用.本文是基础篇,后面会分享下线程池一些高级功能. 1.new Thread的弊端 执行一个异步任务你还只是如下new Thread吗? new Thread(new Runnable() { @Override public void run() { // TODO Auto-generated method stub } }).start(); 那你就out太多了,new Thread的弊端如下: a. 每次ne

求问java 异步编程实现的原理是什么?我一直不明白它与回调的区别,求解,谢谢

问题描述 求问java 异步编程实现的原理是什么?我一直不明白它与回调的区别.假如我在执行某个任务的时候我再开启另外一个线程进行监听,这个与异步的实现有什么区别? 解决方案 应该这样理解同步是和异步进行比较的回调只是一种编程方法,让代码更加的优雅,回调是函数式编程的一种说法,相对于面向对像编程时,"回调"就变成"事件监听"这种说法了我们常说的同步回调,指的就是一个代码执行过程中,需要等到回调函数完全执行完后,才能往 下走.异步回调指的是一个代码执行到回调函数时,他可

Java中终止线程的三种方法_java

Thread.stop, Thread.suspend, Thread.resume 和Runtime.runFinalizersOnExit 这些终止线程运行的方法已经被废弃,使用它们是极端不安全的! 1.线程正常执行完毕,正常结束 也就是让run方法执行完毕,该线程就会正常结束. 但有时候线程是永远无法结束的,比如while(true). 2.监视某些条件,结束线程的不间断运行 需要while()循环在某以特定条件下退出,最直接的办法就是设一个boolean标志,并通过设置这个标志来控制循环