众所周知,在C中,浮点文字(例如1.23
)的类型为double
。因此,任何涉及它们的计算都会提升到两倍。
我正在使用嵌入式实时系统,该系统具有仅支持单精度(float
)数字的浮点单元。我的所有变量都是float
,这个精度就足够了。我根本不需要(也买不起)double
。但每次都像
if (x < 2.5) ...
写道,灾难发生:减速可达两个数量级。当然,直接的答案是写
if (x < 2.5f) ...
但这很容易错过(直到太晚才难以发现),特别是在配置时#?价值为#define
,由一个不那么自律(或刚刚开发)的开发人员在一个单独的文件中。
那么,有没有办法强制编译器将所有(浮点)文字视为float,就像使用后缀f
一样?即使它违反了规范,我也不在乎。或任何其他解决方案?顺便说一句,编译器是gcc。
答案 0 :(得分:77)
-fsingle-precision-constant
标志。它会导致浮点常量以单精度加载,即使这不是精确的。
注意 - 这也将在双精度变量的操作中使用单精度常量。
答案 1 :(得分:50)
使用警告:a = something(); print(a)
警告隐式浮动以进行双重促销,如您的示例所示。 -Wdouble-promotion
会警告您可能仍在为浮动分配双打的情况。
这比仅仅将双值强制转换为最接近的浮点值更好。您的浮点代码仍然符合要求,如果double值保持正值(例如,小于-Wfloat-conversion
(假设为IEEE-754)或大于FLT_DENORM_MIN
,则不会产生任何令人讨厌的意外
答案 2 :(得分:1)
您可以将定义的常量强制转换为(float)
,无论它们在何处使用,优化程序都应该完成其工作。这是一种便携式解决方案。
#define LIMIT 2.5
if (x < (float)LIMIT) ...
答案 3 :(得分:1)
也可以使用-Wunsuffixed-float-constants
标志,也可以将其与上面接受的答案中的其他一些选项组合使用。但是,这可能不会在系统标头中捕获未加前缀的常量。也需要使用-Wsystem-headers
来捕获它们。可能会产生很多警告...