编程博客
002、修改Nuget包位置
001、C#常用的单词
003、收藏的书签
回家准备
004、ASP.NET Core 3.0 gRPC
001、ASP.NET Core 3.0 使用gRPC
002、ASP.NET Core 3.0 gRPC 双向流
003、ASP.NET Core 3.0 gRPC 身份认证和授权
005、飞牛NAS
001、 FnOS飞牛系统实用配置1-应用远程访问(迅雷)
006、DeepSeek
001、DeepSeek 使用指南
007、并发编程
01、并发编程 - 死锁的产生、排查与解决方案
02、并发编程 - 初识线程
03、并发编程 - 线程浅试
04、并发编程 - 线程同步(一)
05、并发编程 - 线程同步(二)
06、并发编程 - 线程同步(三)之原子操作 Interlocked 简介
07、并发编程 - 线程同步(四)之原子操作 Interlocked 详解一
08、并发编程 - 线程同步(五)之原子操作 Interlocked 详解二
09、并发编程 - 线程同步(六)之锁 lock
008、启动项
03、应用--Program 中的 WebApplication
02、主机--Host
01、Program 文件的作用
04、控制反转 IOC 与依赖注入 DI
05、中间件
06、Logger 原理及配置 Log4Net
07、ElasticSearch
本文档使用 MrDoc 发布
-
+
首页
06、并发编程 - 线程同步(三)之原子操作 Interlocked 简介
上一章我们了解了 3 种处理多线程中共享资源安全的方法,今天我们将更近一步,学习一种针对简单线程同步场景的解决方案——Interlocked。  在此之前我们先学习一个概念——原子操作。 # ***01***、原子操作 原子操作,其概念源于化学领域,原子是构成化学元素的普通物质的最小单位;原子也是化学变化中最小的粒子及元素化学性质的最小单位。 借鉴到编程语言中原子操作指:不可分割的操作单元,是指一类不可中断的操作,它在执行时要么全部执行,要么全部不执行,不会被其他操作打断,而执行结果要么全部成功,要不全部失败,没有其他状态。 我们再回忆一下我们学习线程同步的目的——**确保多个线程在访问共享资源时能够按顺序、安全地进行操作**,从而避免并发执行带来的**数据竞争**和**不一致的状态。** 可以说原子操作天然的解决了多线程共享资源安全问题。 在 C#语言中,Interlocked 类提供了一系列可以进行原子操作的工具。 # ***02***、Interlocked 实现原理 Interlocked 的原子操作是基于 CPU 本身实现,是硬件级别的原子指令封装,并且它不需要显式的线程阻塞,因此比传统的锁机制(如互斥锁、信号量等)效率更高,尤其是在高并发的场景下。 线程阻塞是指操作系统把当前线程从运行状态变更为阻塞状态,并且操作系统会把当前线程占用的 CPU 时间片分配给其他线程,使当前线程尽可能少的占用 CPU 时间。在分配 CPU 时间片时会涉及上下文切换等操作。 因此 Interlocked 的非阻塞特性,严格意义上来说并不是锁,但是效率却比锁高得多。 另外如果一个方法在 CPU 层面上被设计为对立不可分割的指令,那么它本质上就是原子的,严格的原子性可以阻止任何抢占的可能。因此在 32 位 CPU 中,一个操作数的大小为 32 位,因此可以提供 32 位即 4 个字节大小及以内的数据类型(如 int,float)进行读写的原子操作。同理 64 位 CPU,则可以提供 64 位级 8 个字节大小及以内的数据类型(如 long,double)进行读写的原子操作。 其实在上一章也举个一个例子,在 32 位 CPU 环境下操作 long 类型,多线程情况下会出现线程不完全问题,因为对于 32 位 CPU,操作一次 long 类型数据至少需要两个原子指令,因此就会出现线程安全问题。 # ***03***、Interlocked 常用方法 Interlocked 方法从.NET Framework 1.1 到目前最新的.NET 9 也经历了长足的发展和完善。可以总结为:支持的操作类型在增加,操作能力也再增加,由早期的简单递增、递减、替换操作到现在的复杂位操作,内存屏障操作等。 下面我们先整体了解一下 Interlocked 有那些方法。  * **Read:** 原子的读取 64 位值; * **Increment:** 原子的递增指定的变量,并返回递增后的新值; * **Decrement:** 原子的递减指定的变量,并返回递减后的新值; * **Add:** 原子的对两个变量求和,将第一个变量替换为两者和,并返回操作后第一个变量的新值; * **Exchange:** 原子的交换两个变量,并返回第一个变量的原始值; * **Exchange:** Exchange 方法的泛型版本; * **CompareExchange:** 原子的比较第一个变量和第三个变量是否相等,如果相等,则将第一个变量替换为第二个变量值,并返回第一个变量的原始值; * **CompareExchange:** CompareExchange 方法的泛型版本; * **And:** 原子的对两个变量进行按位与操作,将第一个变量替换为操作结果,并返回第一个变量的原始值; * **Or:** 原子的对两个变量进行按位或操作,将第一个变量替换为操作结果,并返回第一个变量的原始值; * **MemoryBarrier:** 强制执行内存屏障,作用范围当前线程,无返回值; * **MemoryBarrierProcessWide:** 提供进程范围的内存屏障,确保任何 CPU 的读取和写入无法跨屏障移动; 后面我们将详细讲解每个方法的如何使用。
个人天使
2025年2月10日 10:25
转发文档
收藏文档
上一篇
下一篇
手机扫码
复制链接
手机扫一扫转发分享
复制链接
Markdown文件
PDF文档(打印)
分享
链接
类型
密码
更新密码