问题标签 [volatile]

For questions regarding programming in ECMAScript (JavaScript/JS) and its various dialects/implementations (excluding ActionScript). Note JavaScript is NOT the same as Java! Please include all relevant tags on your question; e.g., [node.js], [jquery], [json], [reactjs], [angular], [ember.js], [vue.js], [typescript], [svelte], etc.

0 投票
3 回答
163 浏览

multithreading - 线程和不安全变量

我在这里列出了代码:Threading and Sockets

这个问题的答案是isListeningvolatile. 正如我所说,该修饰符允许我从另一个线程访问变量。读完MSDN后,我意识到我是从下面新创建的线程进程中读取isListening。

所以,我现在的问题:

  • volatile首选方法,因为我基本上是在对变量发出非线程安全请求吗?我已经阅读了有关 Interlocked 类的信息,并想知道在我的代码中使用它是否会更好。Interlocked 看起来与lock(myObj)正在做的事情相似——但具有更多的“天赋”和控制力。我知道简单地应用一个lock(myObj)代码块isListening是行不通的。

  • 我应该实现 Interlocked 类吗?

感谢您的时间和回复。

0 投票
5 回答
18083 浏览

java - 原始类型的易失性或同步?

在 Java 中,如果变量的大小小于或等于 32 位,则赋值是原子的,但如果大于 32 位则不是。

在双重或长期分配的情况下,使用什么(易失性/同步)更有效?

像,

同步不适用于原始参数。在这种情况下如何使用同步?当然我不想锁定我的班级,所以this不应该使用。

0 投票
2 回答
26602 浏览

multithreading - 我如何理解读内存屏障和易失性

某些语言提供了一个volatile修饰符,该修饰符被描述为在读取支持变量的内存之前执行“读取内存屏障”。

读内存屏障通常被描述为一种确保 CPU 在屏障之后执行读取请求之前已执行屏障之前请求的读取的方法。然而,使用这个定义,似乎仍然可以读取陈旧的值。换句话说,按一定顺序执行读取似乎并不意味着必须咨询主存储器或其他 CPU,以确保后续读取的值实际上反映了系统中在读屏障时的最新值或在读取屏障之后随后写入的值。阅读障碍。

那么,volatile 真的保证读取的是最新的值还是只是(喘气!)读取的值至少与屏障之前的读取一样是最新的?还是其他的解释?这个答案的实际意义是什么?

0 投票
4 回答
3631 浏览

c# - C# volatile 数组项?

我需要一个包含易失性项目的数组,但找不到办法。

这意味着 _arr 引用是可变的,但是它不保证 _arr 对象本身内的项目的任何内容。

有没有办法将 _arr 的项目标记为易失性?

谢谢。

编辑:

以下代码根据 binarycoder 的答案构建。这段代码可以线程安全使用吗?

0 投票
7 回答
4247 浏览

java - 易失的布尔值

如果我有一个 volatile 布尔值(我们称它为有效),那么以下代码在 Java 中是线程安全的吗?

或者,我是否需要同步,因为仅当它为假时才将有效设置为真(因此有效的集合取决于其当前值)?

0 投票
6 回答
982 浏览

java - 并发,对象可见性

我试图弄清楚下面的代码是否存在任何潜在的并发问题。具体来说,与易失性变量相关的可见性问题。Volatile被定义为:这个变量的值永远不会被缓存在线程本地:所有的读写都将直接进入“主内存”

对于上面的单线程执行器

可以使test.state非易失性吗?换句话说,每个连续的 Test.run()(这将顺序发生而不是同时发生,因为再次执行程序是单线程的),总是看到更新的test.state值?如果不是,退出Test.run()是否不会确保在本地对线程所做的任何更改都写回主内存?否则,如果不是在线程退出时,本地所做的更改何时会被写回主内存?

0 投票
4 回答
195 浏览

c# - 确定一个对象何时未被任何其他线程使用而没有锁?

我实现了一个高性能线程安全组件,不使用锁定语句,出于性能原因仅使用 volatile 和 Interlocked。

我在一个包含线程安全实例的类中有 volatile 引用类型成员。此实例仅对几个操作是线程安全的,而对另一个则不是。因此,出于性能原因,在某些情况下,我更喜欢创建新实例而不是更新原始实例,而且它确实工作得更快,特别是因为我不使用任何锁定语句。

因此 volatile 成员可以随时替换为另一个实例, volatile 关键字确保在多线程环境中不会出现任何问题。

这当然工作得很好,但唯一的问题是旧实例的垃圾收集。在测试我的组件的性能时,我发现它在垃圾收集释放的实例上花费了太多时间。

现在我正在寻找一种方法来回收旧实例。问题是我不能在替换时只使用旧实例并重置它的状态,因为可能有另一个线程仍在使用这个实例,我找不到一种方法(没有锁)来保证没有人使用这个实例了。

我如何保证没有线程使用没有锁语句的旧实例?(volatile 和 Interlocked 是首选)

谢谢。

0 投票
8 回答
26778 浏览

c# - .NET 中双重检查锁定需要 volatile 修饰符

多个文本说,在 .NET 中实现双重检查锁定时,您锁定的字段应该应用 volatile 修饰符。但究竟为什么呢?考虑以下示例:

为什么“lock (syncRoot)”不能实现必要的内存一致性?不是真的在“锁定”语句之后读取和写入都将是易失的,因此会实现必要的一致性?

0 投票
2 回答
38686 浏览

c - 易失结构语义

将结构类型变量的实例声明为 volatile 是否足够(如果在可重入代码中访问其字段),还是必须将结构的特定字段声明为 volatile?

措辞不同,以下之间的语义差异(如果有的话)是什么:

我认识到将指针类型的变量声明为 volatile(例如 volatile uint8_t * foo)只会通知编译器 foo 指向的地址可能会改变,而不会声明 foo 指向的值。我不清楚类比是否适用于结构类型的变量。

0 投票
3 回答
1602 浏览

.net - .NET 内存模型、易失性变量和测试和设置:有什么保证?

我知道 .NET 内存模型(在 .NET Framework 上;不是 compact/micro/silverlight/mono/xna/what-have-you)保证对于某些类型(最显着的原始整数和引用)操作保证是原子。

此外,我相信 x86/x64 测试和设置指令 (and Interlocked.CompareExchange) 实际上引用了全局内存位置,因此如果它成功,另一个Interlocked.CompareExchange会看到新值。

最后,我相信该volatile关键字是对编译器的指令,以尽快传播读取和写入,并且不对有关此变量的操作重新排序(对吗?)。

这导致了几个问题:

  1. 我上面的信念是正确的吗?
  2. Interlocked.Read没有 int 的重载,仅适用于 longs(这是 2 个 WORD,因此通常不会以原子方式读取)。我一直认为 .NET 内存模型保证在读取整数/引用时会看到最新的值,但是对于处理器缓存、寄存器等。我开始看到这可能是不可能的。那么有没有办法强制重新获取变量?
  3. volatile 足以解决整数和引用的上述问题吗?
  4. 在 x86/x64 上,我可以假设...

如果有两个全局整数变量 x 和 y,如果我写的话,都初始化为 0:

该 NO 线程将看到 x = 0 和 y = 2(即写入将按顺序发生)。如果它们不稳定,这会改变吗?