如何计算C#中浮点的平方根

Chr*_*ris 7 c# math square-root

如何计算Floatin的平方根C#,类似于Core.SqrtXNA?

Cod*_*aos 15

计算它double然后再回到浮点数.可能有点慢,但应该工作.

(float)Math.Sqrt(inputFloat)
Run Code Online (Sandbox Code Playgroud)

  • @CodeInChaos:请注意,精度损失甚至不是"非常小".假设转换和双精度平方根被正确舍入,这为所有可能的输入提供了正确舍入的单精度平方根. (4认同)
  • @Chris:不,有一个众所周知的浮点分析定理可以保证这会给你正确的结果. (2认同)
  • 由于double的精度远高于"浮动",因此损失将非常小或不存在.通过使用浮动你已经说过你并不关心精度. (2认同)

小智 5

讨厌这样说,但0x5f3759df似乎需要3倍于Math.Sqrt.我只是对计时器进行了一些测试.for循环访问预先计算的数组中的Math.Sqrt导致大约80ms.在相同情况下0x5f3759df导致180 + ms

使用Release模式优化进行了多次测试.

来源如下:

/*
    ================
    SquareRootFloat
    ================
    */
    unsafe static void SquareRootFloat(ref float number, out float result)
    {
        long i;
        float x, y;
        const float f = 1.5F;

        x = number * 0.5F;
        y = number;
        i = *(long*)&y;
        i = 0x5f3759df - (i >> 1);
        y = *(float*)&i;
        y = y * (f - (x * y * y));
        y = y * (f - (x * y * y));
        result = number * y;
    }

    /*
    ================
    SquareRootFloat
    ================
    */
    unsafe static float SquareRootFloat(float number)
    {
        long i;
        float x, y;
        const float f = 1.5F;

        x = number * 0.5F;
        y = number;
        i = *(long*)&y;
        i = 0x5f3759df - (i >> 1);
        y = *(float*)&i;
        y = y * (f - (x * y * y));
        y = y * (f - (x * y * y));
        return number * y;
    }

    /// <summary>
    /// The main entry point for the application.
    /// </summary>
    [STAThread]
    static void Main()
    {
        int Cycles = 10000000;
        Random rnd = new Random();
        float[] Values = new float[Cycles];
        for (int i = 0; i < Cycles; i++)
            Values[i] = (float)(rnd.NextDouble() * 10000.0);

        TimeSpan SqrtTime;

        float[] Results = new float[Cycles];

        DateTime Start = DateTime.Now;

        for (int i = 0; i < Cycles; i++)
        {
            SquareRootFloat(ref Values[i], out Results[i]);
            //Results[i] = (float)Math.Sqrt((float)Values[i]);
            //Results[i] = SquareRootFloat(Values[i]);
        }

        DateTime End = DateTime.Now;

        SqrtTime = End - Start;

        Console.WriteLine("Sqrt was " + SqrtTime.TotalMilliseconds.ToString() + " long");
        Console.ReadKey();
    }
}
Run Code Online (Sandbox Code Playgroud)

  • 说实话,这看起来很偏离主题,但无论如何都很有趣! (3认同)