C语言中的volatile关键字?

29 c volatile

我对C语言中的volatile有疑问.

我读了一些教程,但仍然无法弄清楚,有些人说,volatile告诉编译器优化器,不应该以某种方式优化涉及这个变量的操作.这意味着只要变量的值在寄存器中发生变化,该值就会影响内存.

而且有些人说volatile是指可以通过此代码之外的方式更改值.

我无法理解第二种说法,因此可以通过此代码之外的方式更改volatile变量?怎么样?这两个说对了吗?

Win*_*Oak 41

声明"可以通过此代码之外的方式更改值"基本上意味着另一个程序或硬件可以更新该变量.这完全有可能.考虑这一点的一种方式是将此概念与多个程序之间共享的文件相关联.许多程序可以同时打开,写入和读取文件.当您从文件中读取时,要确保您正在阅读最新的更新,而不是最旧的更新.

回到volatile关键字,在变量之前放置volatile实际上是做同样的事情.它确保您从变量中读取的内容不是基于编译器的优化或程序所具有的变量的旧副本.此外,volatile关键字确保在每次访问时从内存中获取变量.因此,关于volatile关键字,这两个语句都是正确的.

  • @ratzip:是的.变量是存储器中包含值的位置,存储器只是一块硬件(例如RAM芯片).设置了许多计算机系统(键盘,网络,音频输入等),以便外部硬件可以直接修改某些存储位置. (8认同)

avi*_*ldg 19

C不一定适用于计算机.例如,如果您正在为Game Boy Advance开发,您经常会遇到由硬件修改的内存位置,因此您可能无法修改代码中的变量,但无论如何都会对其进行修改.这volatile意味着什么.

通过添加volatile关键字,您告诉编译器"存储在此变量(内存位置)中的值可能会在我的代码执行任何操作时发生更改."

  • @Random:C标准没有定义如何解决`#include`s.这并不意味着它们没用. (5认同)
  • @Random:因为它就是这样的.无论如何,几乎每个平台都需要在某些时候与硬件进行交互. (2认同)

Oli*_*rth 15

请考虑以下任何一种情况:

  • 一个多线程的应用程序,
  • 使用共享内存的应用程序,
  • 在将I/O寄存器映射到地址空间的平台上运行的应用程序,
  • 在后台发生硬件DMA的应用程序.

在每种情况下,都可以在当前线程之外更改内存.

注意" 任何时候变量的值都在寄存器中变化,那么值应该影响内存 "是正确的,只是不太清楚.

  • C规范中没有要求volatile具有获取/释放语义或对多线程代码实际有用的任何其他语义.请记住,不同的线程可能正在对不同处理器上的不一致缓存进行操作; 没有要求编译器实现volatile以将其考虑在内.除非您正在为特定编译器编写代码,并且您知道编译器针对volatile实现了C语言的扩展,否则不应将volatile用于线程语义. (3认同)
  • 但是`volatile`对于多线程代码非常非常有用. (2认同)
  • volatile 在数据可能被异步事件修改的情况下也很有用,例如信号处理程序代码的执行(即信号处理程序代码修改了变量)。 (2认同)

小智 5

可以通过多种方式在程序代码之外更改存储器位置.例如,从磁盘读取的DMA可以写入缓冲区,或者由于设备上的某些事件,存储器映射设备可以更改位置.