原子性 与 可见性

加锁机制既可以确保可见性又可以确保原子性,而volatile变量只能确保可见性。

public class NoVisibility {
    private static boolean ready;
    private static int number;

    private static class ReaderThread extends Thread{
        public void run(){
            while(!ready){
                Thread.yield();
            }
            System.out.println(number);
        }
    }

    public static void main(String[] args){
        new ReaderThread().start();
        number = 45;
        ready = true;
    }
}

(1)Novisibility可能会持续循环,因为ReaderThread可能会看不到写入ready的值。

(2)NoVisibility可能会输出0,因为ReaderThread可能会看到写入ready的值,却没有看到写入number的值。--重排序(在没有同步的情况下,编译器、

处理器、运行时都可能对操作的执行顺序进行调整)

使用volatile的情况:

(1)对变量的写入操作不依赖变量的当前值,或确保只有单个线程更新变量的值。

(2)在访问变量时不需要加锁

时间: 2024-10-30 23:22:34

原子性 与 可见性的相关文章

深入理解Java虚拟机笔记---原子性、可见性、有序性

Java内存模型是围绕着并发过程中如何处理原子性.可见性.有序性这三个特征来建立的,下面是这三个特性的实现原理: 1.原子性(Atomicity) 由Java内存模型来直接保证的原子性变量操作包括read.load.use.assign.store和write六个,大致可以认为基础数据类型的访问和读写是具备原子性的.如果应用场景需要一个更大范围的原子性保证,Java内存模型还提供了lock和unlock操作来满足这种需求,尽管虚拟机未把lock与unlock操作直接开放给用户使用,但是却提供了更

并发编程之原子性、可见性、有序性的简单理解

并发程序正确地执行,必须要保证原子性.可见性以及有序性.只要有一个没有被保证,就有可能会导致程序运行不正确. 原子性:一个操作或多个操作要么全部执行完成且执行过程不被中断,要么就不执行. 可见性:当多个线程同时访问同一个变量时,一个线程修改了这个变量的值,其他线程能够立即看得到修改的值. 有序性:程序执行的顺序按照代码的先后顺序执行. 对于单线程,在执行代码时jvm会进行指令重排序,处理器为了提高效率,可以对输入代码进行优化,它不保证程序中各个语句的执行先后顺序同代码中的顺序一致,但是它会保证保

volatile关键字、原子性和可见性

1.volatile关键字 理解volatile的关键首先要理解处理器缓存和主存. 如果将一个域声明为volatile,那么只要对这个域产生了写操作,那么所有读操作都可以看到这个修改,即volatile域的写操作会向主存刷新. 同步synchronized也会导致向主存中刷新,所以如果一个域完全由synchronized保护就不必设置为volatile. 2.原子性和可见性 可见性: 原子性:

原子性与可见性

一.定义 1.可见性 在多核处理器中,如果多个线程对一个变量(假设)进行操作,但是这多个线程有可能被分配到多个处理器中运行,那么编译器会对代码进行优化,当线程要 处理该变量时,多个处理器会将变量从主存复制一份分别存储在自己的片上存储器中,等到进行完操作后,再赋值回主存.(这样做的好处是提高了运行的速度,因 为在处理过程中多个处理器减少了同主存通信的次数):同样在单核处理器中这样由于“备份”造成的问题同样存在! 这样的优化带来的问题之一是变量可见性——如果线程t1与线程t2分别被安排在了不同的处理

内存管理_原子性、可见性、有序性

原子性:即一个操作或者多个操作 要么全部执行并且执行的过程不会被任何因素打断,要么就都不执行 比如存取款操作,存款和取款操作必须全部完成,或者全部不完成. 可见性:指当多个线程访问同一个变量时,一个线程修改了这个变量的值,其他线程能够立即看得到修改的值. eg: //Thread 1 int i = 0; i = 10; //Thread 2 j = i; 假若执行Thread1的是CPU0,执行Thread2的是CPU1.由上面的分析可知,当Thread1执行 i =10这句时,会先把i的初始

并发之原子性、可见性、有序性

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

java并发特性:原子性、可见性、有序性

要想并发程序正确地执行,必须要保证原子性.可见性以及有序性.只要有一个没有被保证,就有可能会导致程序运行不正确. 1.原子性(Atomicity) 原子性是指在一个操作中就是cpu不可以在中途暂停然后再调度,既不被中断操作,要不执行完成,要不就不执行. 如果一个操作时原子性的,那么多线程并发的情况下,就不会出现变量被修改的情况 比如 a=0:(a非long和double类型) 这个操作是不可分割的,那么我们说这个操作时原子操作.再比如:a++: 这个操作实际是a = a + 1:是可分割的,所以

7.三大性质总结:原子性、可见性以及有序性

1. 三大性质简介 在并发编程中分析线程安全的问题时往往需要切入点,那就是两大核心:JMM抽象内存模型以及happens-before规则(在这篇文章中已经经过了),三条性质:原子性,有序性和可见性.关于synchronized和volatile已经讨论过了,就想着将并发编程中这两大神器在 原子性,有序性和可见性上做一个比较,当然这也是面试中的高频考点,值得注意. 2. 原子性 原子性是指一个操作是不可中断的,要么全部执行成功要么全部执行失败,有着"同生共死"的感觉.及时在多个线程一起

Java并发编程三个性质:原子性、可见性、有序性

并发编程 并发程序要正确地执行,必须要保证其具备原子性.可见性以及有序性:只要有一个没有被保证,就有可能会导致程序运行不正确 线程不安全在编译.测试甚至上线使用时,并不一定能发现,因为受到当时的CPU调度顺序,线程个数.指令重排的影响,偶然触发 线程安全的定义 比如说一个类,不论通过怎样的调度执行顺序,并且调用处不用对其进行同步操作,其都能表现出正确的行为,则这个类就是线程安全的 并发编程三个概念 原子性: 一个操作或多个操作要么全部执行且执行过程不被中断,要么不执行 可见性: 多个线程修改同一

线程的共享性、互斥性、原子性、可见性、有序性

参考链接:http://www.cnblogs.com/paddix/p/5374810.html 一.共享性 多个线程之间共享同一个变量,容易引发多线程安全问题.反之,如果每个数据都只是在自己的线程中使用,只属于某一个线程,那么这个数据则为安全的. 二.互斥性 资源互斥是指只允许一个访问者对其进行访问,具有唯一性和排他性.对于共享数据,如果我们只进行读数据,即使没有互斥性,我们也不需要担心其安全,但如果是写操作,则容易引起线程安全问题. 三.原子性 原子性是指对数据的操作是一个独立的.不可分割