能否在不失精度的情况下将浮点数转换为双精度,然后再转回去?我的意思是第一个浮点数应该与结果浮点数完全相同,位对位地匹配。
能否在不失精度的情况下将浮点数转换为双精度,然后再转回去?我的意思是第一个浮点数应该与结果浮点数完全相同,位对位地匹配。
是的,我们可以进行测试:
float fl = float.NegativeInfinity;
long cycles = 0;
while (true)
{
double dbl = fl;
float fl2 = (float)dbl;
int flToInt1 = new Ieee754.Int32SingleConverter { Single = fl }.Int32;
int flToInt2 = new Ieee754.Int32SingleConverter { Single = fl2 }.Int32;
if (flToInt1 != flToInt2)
{
Console.WriteLine("\nDifferent: {0} (Int32: {1}, {2})", fl, flToInt1, flToInt2);
}
if (fl == 0)
{
Console.WriteLine("\n0, Sign: {0}", flToInt1 < 0 ? "-" : "+");
}
if (fl == float.PositiveInfinity)
{
fl = float.NaN;
}
else if (float.IsNaN(fl))
{
break;
}
else
{
fl = Ieee754.NextSingle(fl);
}
cycles++;
if (cycles % 100000000 == 0)
{
Console.Write(".");
}
}
Console.WriteLine("\nDone");
Console.ReadKey();
还有实用类:
public static class Ieee754
{
[StructLayout(LayoutKind.Explicit)]
public struct Int32SingleConverter
{
[FieldOffset(0)]
public int Int32;
[FieldOffset(0)]
public float Single;
}
public static float NextSingle(float value)
{
int bits = new Int32SingleConverter { Single = value }.Int32;
if (bits >= 0)
{
bits++;
}
else if (bits != int.MinValue)
{
bits--;
}
else
{
bits = 0;
}
return new Int32SingleConverter { Int32 = bits }.Single;
}
}
Ieee754
类……我在一年前尝试IEEE754时就写过它)。 - xanatos是的,由于每个浮点数都可以精确地表示为双精度浮点数,因此往返转换将给您与开始时完全相同的精确值。
在您要求它们按位完全相同时,有一个可能的技术例外:有多个位模式对应于NaN值(这通常称为“NaN有效负载”)。据我所知,没有严格的要求必须保留它:您仍将获得NaN,只是可能会稍有不同。