浮点数是否可以通过双精度转换回来而不失去精度?

5

如果我有一个 C# 的 float,我是否可以将其转换为 double 而不会丢失任何精度?

如果那个 double 再被转换回 float,它的值是否完全相同?

2个回答

9
是的。IEEE754浮点数(这是C#必须使用的)保证了以下几点:
  1. float 转换为 double 会完全保留相同的值。

  2. 将该 double 转换回 float 可以精确地恢复原始的 float

double 的集合是 float 的超集。
请注意,这也适用于 NaN+Infinity-Infinity。零的符号也得到保留。

7

让我们用代码来测试一下:

[Fact]
public void IsFloatRoundTrippableToDouble()
{
    var bits = default(FloatUnion);
    bits.FloatData = float.MinValue;

    var testBits = default(FloatUnion);

    // ReSharper disable once LoopVariableIsNeverChangedInsideLoop
    while (bits.FloatData <= float.MaxValue)
    {
        var d = (double)bits.FloatData;
        testBits.FloatData = (float)d;

        if (bits.IntData != testBits.IntData)
            Assert.True(false);

        bits.IntData -= 1;
    }
}

[StructLayout(LayoutKind.Explicit)]
private struct FloatUnion
{
    [FieldOffset(0)] public uint IntData;
    [FieldOffset(0)] public float FloatData;
}

该代码会测试MinValueMaxValue之间的每个float值(除了NaN,无穷大等)。比较它们在内存中的字节表示以确保不进行其他转换。

虽然测试约40亿个可能的浮点数看起来很疯狂,但实际上在我的机器上只需大约11秒。

而且,该转换是安全的。从floatdouble再转回来不会丢失任何信息。


1
我很困惑你为什么发布这个,难道不应该放在文档中吗? - Alfie Goodacre
4
我不同意。这仍然是一个好问题,也是一个好答案。回答自己的问题没有伤害。 - Bathsheba

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接