【问题标题】:Is there an equivalent of Java 'volatile' in C++?C++ 中是否存在相当于 Java 'volatile' 的东西?
【发布时间】:2015-09-02 18:22:32
【问题描述】:

在Java中,有时当从不同线程访问同一个变量时,每个线程都会创建自己的变量副本,因此如果我将一个线程中的变量值设置为10然后我尝试读取这个变量的值来自另一个线程,我不会得到10(因为第二个线程正在从另一个变量的副本中读取!)。

要在Java中解决这个问题,我所要做的就是使用关键字volatile,例如:

volatile int i = 123;

这个问题在 C++ 中也存在吗?如果是这样,我该如何解决?

注意:我使用的是 Visual C++ 2010。

【问题讨论】:

  • 最简单的方法是std::atomic。
  • std::atomic 在 VC2010 中不可用。 boost::atomic 是一个选项。
  • 请阅读 volatile 是什么(在 Java 中)。看来您高估了它的功能。不,没有volatile,它不是“每个线程一个副本”。
  • @DJClayworth 也许这就是 OP 的想法,也许不是,这就是我首先写它的原因(他应该阅读更多关于它的内容)
  • 好吧,threadcopy 问题似乎解决了,但仍然:阅读 Java 中的 volatile。它不是在任何情况下都可以确保线程安全的完美解决方案。而 C++ volatile 则更少。

标签: java c++ windows multithreading


【解决方案1】:

是的,C++ 中也存在同样的问题。但是由于 C 已经引入了具有不同含义的关键字 volatile(与线程无关),并且 C++ 以相同的方式使用它们关键字,因此您不能像在 Java 中那样在 C++ 中使用 volatile

相反,您最好使用std::atomic<T>(或 boost::)。它并不总是最有效的选择,但它很简单。如果这被证明是一个瓶颈,您可以放松std::atomic 使用的std::memory_order

话虽如此,关于标准 C++,MSVC++ 作为扩展确实保证了多个线程可以访问共享的volatile 变量。 IIRC,所有线程最终都会看到相同的值,并且没有线程会及时返回。 (也就是说,如果 0 和 1 依次写入一个变量,则没有线程会看到序列 1,0)

【讨论】:

  • std::atomic 不是只能在 C++11 中使用吗?
  • @paul:是的,但这是合乎逻辑的,因为 C++03 甚至没有线程。
  • 那么如果我使用的是 Visual C++ 2010,我该如何解决这个问题,Windows API 是否提供了解决方案?
  • @paul:使用 boost - C++11 解决方案是直接从 Boost 派生的。升级到最新版本的 MSVC 后,您可能可以将 using boost::atomic 替换为 using std::atomic
  • 如果我只使用C和Windows API线程,你知道如何解决这个问题吗?
猜你喜欢
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2019-11-18
  • 2016-06-03
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2011-06-19
相关资源
最近更新 更多