首页
学习
活动
专区
圈层
工具
发布
社区首页 >问答首页 >C语言中的转换表达式语义

C语言中的转换表达式语义
EN

Stack Overflow用户
提问于 2019-06-18 00:09:04
回答 1查看 147关注 0票数 3

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

如果表达式的值以比强制转换命名的类型(6.3.1.8)所需的范围或精度更大的范围或精度表示,则强制转换指定一个转换,即使表达式的类型与命名类型相同,并移除任何额外的范围和精度。

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

你能提供一个例子来说明这个规则吗?现在看上去有点混乱。

EN

回答 1

Stack Overflow用户

回答已采纳

发布于 2019-06-18 01:14:23

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

代码语言:javascript
复制
float f = 1.234f * 5.678f;

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

在C17 5.2.4.2.2/9中具体说明了这一点:

除了赋值和转换(移除所有额外范围和精度)外,由具有浮动操作数的运算符和受通常算术转换和浮动常量影响的值所产生的值将被计算为一种格式,其范围和精度可能大于该类型所需的范围和精度。使用评估格式的特点是FLT_EVAL_METHOD的实现定义值:

  • −1不确定;
  • 0只根据类型的范围和精度评估所有操作和常数;
  • 1计算浮子型的运算量和常数,双倍于双型的范围和精度,用长双型的范围和精度评价长双运算和常数;
  • 2根据长双类型的范围和精度评估所有操作和常量。

FLT_EVAL_METHOD的所有其他负值都描述了实现定义的行为。

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

您引用的文本重申cast操作符将结果转换回强制转换类型,例如:

代码语言:javascript
复制
float f = 1.234f * 5.678f + 9.012f;

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

代码语言:javascript
复制
float f = (float)(1.234f * 5.678f) + 9.012f;
票数 4
EN
页面原文内容由Stack Overflow提供。腾讯云小微IT领域专用引擎提供翻译支持
原文链接:

https://stackoverflow.com/questions/56640229

复制
相关文章

相似问题

领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档