`

Java线程访问中的CPU原语应用

阅读更多
Java线程访问中的CPU原语应用
2009年04月28日 星期二 23:05
CPU原语-比较并交换(CompareAndSet),实现非阻塞算法

什么是CAS?

cas是现代CPU提供给并发程序使用的原语操作. 不同的CPU有不同的使用规范.

在 Intel 处理器中,比较并交换通过指令的 cmpxchg 系列实现。
PowerPC 处理器有一对名为“加载并保留”和“条件存储”的指令,它们实现相同的目地;
MIPS 与 PowerPC 处理器相似,除了第一个指令称为“加载链接”。


CAS 操作包含三个操作数 —— 内存位置(V)、预期原值(A)和新值(B)

什么是非阻塞算法?

一个线程的失败或挂起不应该影响其他线程的失败或挂起.这类算法称之为非阻塞(nonblocking)算法

对比阻塞算法:
如果有一类并发操作, 其中一个线程优先得到对象监视器的锁, 当其他线程到达同步边界时, 就会被阻塞.
直到前一个线程释放掉锁后, 才可以继续竞争对象锁.(当然,这里的竞争也可是公平的, 按先来后到的次序)


CAS 原理:

我认为位置 V 应该包含值 A;如果包含该值,则将 B 放到这个位置;否则,不要更改该位置,只告诉我这个位置现在的值即可。

CAS使用示例(jdk 1.5 并发包 AtomicInteger类分析

/**
* Atomically sets to the given value and returns the old value.
*
* @param newValue the new value
* @return the previous value
*/ public final int getAndSet(int newValue) {
for (;;) {
int current = get();
if (compareAndSet(current, newValue))
return current;
}
}

public final boolean compareAndSet(int expect, int update) {
return unsafe.compareAndSwapInt(this, valueOffset, expect, update);
}

这个方法是, AtomicInteger类的常用方法, 作用是, 将变量设置为指定值, 并返回设置前的值.
它利用了cpu原语compareAndSet来保障值的唯一性.

另, AtomicInteger类中, 其他的实用方法, 也是基于同样的实现方式.
比如 getAndIncrement, getAndDecrement, getAndAdd等等.

CAS语义上存在的"ABA 问题"

什么是ABA问题?

假设, 第一次读取V地址的A值, 然后通过CAS来判断V地址的值是否仍旧为A, 如果是, 就将B的值写入V地址,覆盖A值.

但是, 语义上, 有一个漏洞, 当第一次读取V的A值, 此时, 内存V的值变为B值, 然后在未执行CAS前, 又变回了A值.
此时, CAS再执行时, 会判断其正确的, 并进行赋值.

这种判断值的方式来断定内存是否被修改过, 针对某些问题, 是不适用的.

为了解决这种问题, jdk 1.5并发包提供了AtomicStampedReference(有标记的原子引用)类, 通过控制变量值的版本来保证CAS正确性.

其实, 大部分通过值的变化来CAS, 已经够用了.


jdk1.5原子包介绍(基于volatile)

包的特色:

1, 普通原子数值类型AtomicInteger, AtomicLong提供一些原子操作的加减运算.

2, 使用了解决脏数据问题的经典模式-"比对后设定", 即 查看主存中数据是否与预期提供的值一致,如果一致,才更新.

3, 使用AtomicReference可以实现对所有对象的原子引用及赋值.包括Double与Float,
但不包括对其的计算.浮点的计算,只能依靠同步关键字或Lock接口来实现了.

4, 对数组元素里的对象,符合以上特点的, 也可采用原子操作.包里提供了一些数组原子操作类
AtomicIntegerArray, AtomicLongArray等等.

5, 大幅度提升系统吞吐量及性能.
分享到:
评论

相关推荐

    编写多线程的 Java 应用程序

    Java Thread API 提供了在Java应用程序中实现多线程的能力,从而允许程序在处理后台任务的同时保持用户界面的响应性。Alex Roetter的文章深入探讨了Java的多线程概念,包括可能遇到的问题以及如何解决这些问题。 ...

    Java线程面试题

    Java线程面试题是Java开发者在面试中常常遇到的核心领域,因为并发处理是现代软件开发中的关键部分。Java语言的并发支持使得它在企业级应用中广泛应用。掌握线程和并发编程不仅能提升程序性能,也是高级Java开发职位...

    java面试题_多线程(68题).pdf

    Java中的多线程是面试中常见的话题,涵盖了操作系统的基础概念以及Java并发库的高级特性。...了解这些概念有助于深入理解Java多线程编程,它们在面试中常常作为考察点,对于开发高效、可靠的并发应用程序至关重要。

    java 多线程PDF档

    Java中的线程池(ExecutorService)是另一种优化多线程应用的方法。通过线程池,我们可以预先创建一定数量的线程,然后将任务提交到线程池处理,而不是每次需要时都创建新线程。这不仅可以减少线程创建和销毁的开销...

    java多线程设计模式详解.rar

    在Java中,多线程可以提高程序的执行效率,使多个任务能够同时运行,从而充分利用CPU资源。本文将深入探讨Java多线程设计模式,旨在帮助开发者理解和掌握这些模式,提升编程技能。 1. **生产者消费者模式**:这是...

    Java并发编程全景图.pdf

    在多处理器环境中,非统一内存访问(NUMA)架构、硬件共享内存、内存栅栏和CPU缓存等都是影响并发性能的因素。 13. Java并发编程展望 摩尔定律是衡量硬件发展速度的重要指标,它预言了处理器性能的增长趋势。Java...

    使用线程添加数据

    当多个线程访问共享资源,如数据库连接或全局变量,如果没有正确的同步机制,可能会出现数据不一致、死锁等问题。为此,我们需要使用锁(如Java的`synchronized`关键字或Python的`Lock`对象)、信号量、条件变量等...

    java面试题_多线程(68题)

    38. **线程的同步原语**:如信号量、事件对象、条件变量等,了解其在Java中的实现。 39. **线程安全的日志记录**:如何在多线程环境中保证日志的正确性和一致性。 40. **线程安全的计数器**:如`AtomicInteger`, `...

    JAVA并发编程实践-线程安全-学习笔记

    在Java并发编程中,线程安全是一个至关重要的概念,它涉及到多线程环境下对共享数据的正确管理和访问。线程安全意味着当多个线程同时访问一个对象或数据时,对象的状态能够保持一致性和完整性,不会因为并发导致数据...

    线程间的调用

    互斥锁用于保护共享资源,确保同一时间只有一个线程访问;读写锁允许多个读取线程并发访问,但写入时会独占资源;信号量可以控制对有限资源的访问数量;条件变量则用于线程在满足特定条件时进行等待和唤醒。 在实践...

    多线程小例子

    在编程领域,多线程是实现并发执行任务的关键技术,特别是在服务器端开发、GUI应用程序以及高性能计算中。本文将深入探讨“多线程小例子”所涉及的核心概念、原理及其实现方法,以帮助理解其在实际应用中的价值。 ...

    Java 并行机制的核心

    - **等待与通知**:线程可以通过调用监视器中的`wait`方法让出CPU并等待,而当条件满足时,其他线程可以调用`notify`或`notifyAll`唤醒等待中的线程。 ##### 2.3 原子字段赋值(Atomic Field Assignment) 在Java...

    跨线程提交数据

    在多线程编程中,"跨线程提交数据"是一个重要的概念,特别是在并发处理和优化应用程序性能时。本文将深入探讨这一主题,旨在为初学者提供一个全面的理解。 首先,我们要明白什么是线程。线程是操作系统分配CPU时间...

    线程相关技术26.rar_线程相关技术

    在现代软件开发中,线程的使用越来越广泛,特别是在高并发和实时性要求较高的应用中。本资料"线程相关技术26.rar"主要涵盖了线程的创建、终止、休眠、挂起以及优先级等核心概念,这些都是理解和掌握线程编程的关键。...

    Java-turn学习代码

    7. **Java多线程与并发**:在处理大量并发请求时,Java的多线程和并发控制原语(如`ExecutorService`、`Semaphore`等)是必不可少的。 8. **错误处理与调试**:开发过程中,需要考虑网络异常、超时、连接断开等问题...

    聊聊Java和CPU的关系

    其次,Java中的锁机制,如`synchronized`和`java.util.concurrent`包中的工具类,利用CPU的锁原语来实现线程间的同步。例如,`AtomicInteger`类的实现中,内部使用了`Unsafe`类,通过CPU的原子操作(如CAS,Compare ...

    Java操作系统的工具和分析.pdf

    在Java性能调优的过程中,了解操作系统工具和分析是至关重要的,因为这可以帮助我们洞察应用程序内部的行为和资源使用情况。为了有效地进行性能优化,我们需要全面掌握性能分析工具,这些工具能够帮助我们深入理解...

    实现Java高并发隔离 模拟

    1. **线程局部存储(ThreadLocal)**:Java中的`ThreadLocal`类提供了一种线程安全的方式,每个线程都有自己的副本,互不干扰。这样可以避免共享数据导致的并发问题,但需要注意内存泄漏的问题。 2. **锁...

    DuoXiancheng.rar_多线程 进度条

    在IT领域,多线程是一种常见的编程技术,用于在单个进程中同时执行多个任务,以提高应用程序的效率和响应性。在本项目"DuoXiancheng.rar"中,重点是实现两个独立的进度条,这通常涉及到并发处理和用户界面的更新。...

Global site tag (gtag.js) - Google Analytics