4

volatile就像标题所说的那样 -在单线程编程的上下文中是否有任何有用的情况?我知道它用于确保始终在内存中实际检查变量的值,所以在任何情况下,该值可能会以应用程序/编译器不会注意到的方式发生变化(在 ST 应用程序中)?

我将这个问题与语言无关,因为我不知道它们之间的任何差异会影响这个问题的答案。但如果有的话请告诉我。

编辑:正如向我指出的那样,这个问题与语言无关。然后我将其具体化为 C++(我已经读过 C++ 版本也存在差异,但我希望它们还不足以使这个问题过于宽泛)。

4

3 回答 3

4

这是 C 和 C++ 的答案

是的!当变量映射到硬件寄存器(例如 I/O 设备)时。硬件修改寄存器,独立于应用程序。

例子:

extern volatile uint32_t MY_DEVICE_START; // write-only register
extern volatile const uint32_t MY_DEVICE_STATUS; // read-only register
extern volatile uint32_t MY_DEVICE_DATA; // read-write register

...
MY_DEVICE_DATA = 42; // send input to the device
MY_DEVICE_START = 1; // start the device
while (MY_DEVICE_STATUS == 0) {} // busy-wait for the device to finish
int result = MY_DEVICE_DATA; // read output from the device
...

至少在 C/C++ 中这是主要原因。Volatile 甚至不推荐用于多线程使用

于 2016-02-04T10:37:27.987 回答
3

其他答案已经解决了问题volatile,但我想给出一个真实的例子,我在什么时候volatile有用(不尝试读取/写入特殊的硬件内存位置)。

volatile在 C 或 C++ 程序中可能有用的一个示例是调试。考虑以下示例:

void do_thing(const std::vector<int>& v) {
    if (v.empty()) {
        do_thing_1();
    } else {
        do_thing_2();
    }
}

如果我想测试上述函数并在调试时强制它采用真或假分支,我可以volatile在 if 条件中插入一个变量:

void do_thing(const std::vector<int>& v) {
    volatile bool condition = v.empty();
    if (condition) {
        do_thing_1();
    } else {
        do_thing_2();
    }
}

我这样做是为了volatile让优化器不会完全优化掉变量。这使得在 上设置断点变得简单if,然后我可以修改condition(无需修改v)。

我也可以创建condition一个static变量,这样我就不必一直打断点:我可以打一次,设置它,然后它会“记住”我的选择。

当然,这是一种 hack,但我发现它在某些特定情况下非常有用。

于 2016-02-04T16:09:08.077 回答
1

单线程程序也可以进行信号处理,甚至在非多线程平台上也可以使用硬件中断处理,因此在处理函数中修改的非局部变量应声明为volatile.

ps答案或多或少是通用的,并且可能不正确,具体取决于上面已经提到的语言。

于 2016-02-04T10:56:19.477 回答