C 中的 Cast 表达式语义

标签 c casting floating-point language-lawyer precision

我对标准 6.5.4/6 中的以下措辞感到困惑:

If the value of the expression is represented with greater range or precision than required by the type named by the cast (6.3.1.8), then the cast specifies a conversion even if the type of the expression is the same as the named type and removes any extra range and precision.

我无法理解的是,如果命名类型和表达式的类型相同,表达式的值怎么会有一些额外的范围或精度。

您能否提供一个示例来说明该规则?现在看起来有点困惑。

最佳答案

标准允许以比表达式类型更高的精度计算 float ;例如:

float f = 1.234f * 5.678f;

允许编译器将操作数转换为long double,进行乘法运算,然后再转换回float。这样做的理由是,在许多处理器上,仅使用特定的浮点寄存器大小进行计算会更快,而且通常人们不关心获得精度。

这是在 C17 5.2.4.2.2/9 中指定的:

Except for assignment and cast (which remove all extra range and precision), the values yielded by operators with floating operands and values subject to the usual arithmetic conversions and of floating constants are evaluated to a format whose range and precision may be greater than required by the type. The use of evaluation formats is characterized by the implementation-defined value of FLT_EVAL_METHOD:

  • −1 indeterminable;
  • 0 evaluate all operations and constants just to the range and precision of the type;
  • 1 evaluate operations and constants of type float and double to the range and precision of the double type, evaluate long double operations and constants to the range and precision of the long double type;
  • 2 evaluate all operations and constants to the range and precision of the long double type.

All other negative values for FLT_EVAL_METHOD characterize implementation-defined behavior.

因此您可以检查 FLT_EVAL_METHOD 以了解编译器是否会这样做,但您不一定能自己控制设置。


您引用的文本重申了强制转换运算符将结果转换回强制转换的类型,例如:

float f = 1.234f * 5.678f + 9.012f;

理论上可以给出比以下更准确的结果:

float f = (float)(1.234f * 5.678f) + 9.012f;

关于C 中的 Cast 表达式语义,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/56640229/

相关文章:

c - 如何在使用 fgets() 读取一行后返回到上一行的开头?

c - 优化以及为什么 openmp 比顺序方式慢得多?

Python 浮点格式 - 类似于 "g",但数字更多

c - 动态长度数组

c - 在c中按索引偶数或奇数将数组拆分为两个数组

c++ - 指向函数指针数组的指针

mysql - 将日期字段复制到日期时间的最佳方法?

javascript - 在运行时强制执行类型

c# - float 的乘法性能不一致

java - mysql 中的 float 和 double 数据类型不存储我的 java 程序所需的完整数字