[英]C++ volatile object, nonvolatile member
在问题中:假设我有一小段这样的代码:
#include <iostream>
using namespace std;
struct foo {
int a;
foo() : a(12) {};
};
int
main()
{
volatile foo x;
return 0;
}
用g++ -g -O2
编译,结果证明x
初始化是最优化的。
然而那个:
#include <iostream>
using namespace std;
struct foo {
volatile int a;
foo() : a(12) {};
};
int
main()
{
volatile foo x;
return 0;
}
调用构造函数。
如果我尝试使用代码中的变量,(即cout << foo.a << endl;
),汇编输出在两种情况下都是等效的。
我是否得到以下权利:
在第一种情况下,根本无法访问结构,因此它完全被优化掉了。
在第二个中,struct的字段被指示为在构造期间也可以改变的字段,因此无论如何都调用foo()。
补充:我试过摆弄上面的代码:调用像while(foo.a--);
按预期工作,它实际上发生而不是在优化期间被结果删除/替换,因此看起来挥发性实际上是继承的,但是ctor在这种奇怪的(或者至少在第一次意外)方式中表现。
编辑2:
我用clang和MSVC检查它,它的行为与gcc相同。
我的理解如下(我不确定):
在C ++中, volatile
关键字强制编译器不要优化看似冗余的加载和存储到内存,即如果你有这样的示例代码:
int x = 5;
x = 6;
它不会改为:
int x = 6;
这是因为x
可能指向内存中的某个地址,这是其他人读取的,而您在程序中并未真正读取它(想象您通过写入某个内存地址,通过USART将一些配置发送到微控制器,并且微控制器从该地址读取它的配置 - 如果编译器要优化对该存储器的写入,则整个程序将发生故障)。
必须记住的另一件事是,当一个类的实例用volatile
说明符声明时,它的成员继承这个说明符(正如Igor Tandetnik在评论中指出的那样,指的是C ++标准)。 但这不是全部真相,因为为了获得volatile
行为,你必须调用标记为volatile
成员函数 - 类似于将成员函数标记为const
(请参见: http://www.devx。 com / tips / Tip / 13671 )。 因为AFAIK ctors / dtors不能用volatile
关键字标记(如在定义volatile类对象中 ),所以你必须稍微改变你的代码(也许从ctor中调用volatile成员函数会做的事情,但这只是猜测) 。
声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.