c# - 在 C# 中转换为 'float' 时,“const float”值不同于 'int'

标签 c# .net compiler-bug

你们谁能解释为什么会这样?

static void Main()
{
    const float xScaleStart = 0.5f;
    const float xScaleStop = 4.0f;
    const float xScaleInterval = 0.1f;
    const float xScaleAmplitude = xScaleStop - xScaleStart;

    const float xScaleSizeC = xScaleAmplitude / xScaleInterval;

    float xScaleSize = xScaleAmplitude / xScaleInterval;

    Console.WriteLine(">const float {0}, (int){1}", xScaleSizeC, (int)xScaleSizeC);

    Console.WriteLine(">      float {0}, (int){1}", xScaleSize, (int)xScaleSize);

    Console.ReadLine();
}

输出:

>const float 35, (int)34
>      float 35, (int)35

我知道 0.1 的二进制表示实际上是 0.09999990463256835937,但为什么使用“const float”而不是“float”会发生这种情况?这是否被视为编译器错误?

为了记录,代码编译成:

private static void Main(string[] args)
{
    float xScaleSize = 35f;
    Console.WriteLine(">const float {0}, (int){1}", 35f, 34);
    Console.WriteLine(">      float {0}, (int){1}", xScaleSize, (int)xScaleSize);
    Console.ReadLine();
}

最佳答案

这个“为什么”基本上可以归结为这样一个事实,即在处理 float 数据时,可能会使用比为 float 指定的精度更高的内部表示double。这在虚拟执行系统 ​​(VES) 规范(Partition I 的第 12 节)中明确满足:

floating-point numbers are represented using an internal floating-point type. In each such instance, the nominal type of the variable or expression is either float32 or float64, but its value can be represented internally with additional range and/or precision

然后我们有:

The use of an internal representation that is wider than float32 or float64 can cause differences in computational results when a developer makes seemingly unrelated modifications to their code, the result of which can be that a value is spilled from the internal representation (e.g., in a register) to a location on the stack.

现在,根据C# language specification :

The compile-time evaluation of constant expressions uses the same rules as run-time evaluation of non-constant expressions, except that where run-time evaluation would have thrown an exception, compile-time evaluation causes a compile-time error to occur.

但正如我们在上面观察到的,规则实际上有时允许使用更高的精度,而何时使用这种增强的精度实际上并不在我们的直接控制之下。


显然,在不同的情况下,结果可能与您观察到的完全相反 - 编译器可能已降低精度,而运行时可能会保持较高的精度。

关于c# - 在 C# 中转换为 'float' 时,“const float”值不同于 'int',我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/24016294/

相关文章:

c# - 如何在 C# 中单击时将鼠标指针更改为图像

C# 编译器错误 : allows for conversion from Nullable<decimal> to decimal

c# - 为什么这个协方差声明可以编译?

c# - 在没有序列化的情况下克隆对象

c# - 分配不同结果的最佳方式?

c# - 泛型类型仅在java中属于类类型

c++ - 当 C++ 从函数的返回值将元素存储到 std::vector 时出现意外结果

c# - SQL LIKE 查询到 C# 代码

c# - 用于中等长度任务的 WCF 集群

c# - 通过堆栈的异步/等待行为