我的代码中有一个函数,如下所示:
bool foo(ObjectType& object){
//code
const float result = object.float_data + object.bool_data * integer_data;
//code
}
Run Code Online (Sandbox Code Playgroud)
在寻找错误时,我发现result
有时会有不正确的值,原因是有时bool
*integer
被计算为255*integer
而不是1*integer
。
C++ 说在整数上下文中bool
会转换为零或一,所以我不明白这一点。我与bool
代码中的其他部分相乘,效果很好。这也是随机的:有时会转换为1
,有时会转换为255
。调试器还分别显示true
或255
。当这个错误发生时,它总是发生在该执行中。重新编译代码没有任何效果,它仍然随机发生。
根据C++17 7.14 Boolean conversions
,强制将非布尔值转换为布尔值是标准转换过程的一部分,这意味着它实际上是在为布尔值分配某些值时完成的:
算术、无范围枚举、指针或指向成员类型的指针的纯右值可以转换为 类型的纯右值
bool
。零值、空指针值或空成员指针值将转换为false
; 任何其他值都会转换为true
. 对于直接初始化 (11.6),类型的纯右值std::nullptr_t
可以转换为类型的纯右值bool
;结果值为false
。
例如,如果您没有初始化它,或者您以将其视为非布尔值的方式初始化它,则不能保证布尔值为零或一:
void someFunction() {
bool xyzzy; // Set to some arbitrary value.
memcpy(&xyzzy, "x", 1); // Very contrived, wouldn't pass my
// own code review standards :-)
}
Run Code Online (Sandbox Code Playgroud)
因此,我要考虑的第一件事是确保您正确初始化/分配它。
事实上,现在我很少在没有显式初始化变量的情况下将其存在。即使它后来在使用前发生了变化,我宁愿依赖编译器来解决这个问题,并在它认为有用的情况下进行优化。
但是您可以通过按预期使用布尔值来解决此问题。换句话说,作为真理的宝库,而不是作为整体价值来评估它们。试试这个:
const float result = object.float_data + (object.bool_data ? integer_data : 0);
Run Code Online (Sandbox Code Playgroud)
无论是bool_data
:
integer_data
一个未正确初始化的布尔值(尽管你的结果会受到怀疑 - 我的意思是你永远不会在你的 中添加超过一个float_result
);或者