4

如何在不使用 C# 中的内置数学函数的情况下计算以 2 为底的对数?

我在应用程序中反复使用 Math.Log 和 BigInteger.Log 数百万次,它变得非常缓慢。

我对使用二进制操作来实现相同的替代方案感兴趣。请记住,如果有助于加快执行时间,我可以使用对数近似值。

4

5 回答 5

4

假设您只对对数的整数部分感兴趣,您可以执行以下操作:

static int LogBase2(uint value)
{
    int log = 31;
    while (log >= 0)
    {
        uint mask = (1 << log);
        if ((mask & value) != 0)
            return (uint)log;
        log--;
    }
    return -1;
}

(请注意,0 的返回值是错误的;它应该是负无穷大,但整数数据类型没有这样的值,所以我返回 -1)

于 2012-08-18T23:32:05.370 回答
2

http://graphics.stanford.edu/~seander/bithacks.html

于 2012-08-18T23:31:21.533 回答
1

对于 BigInteger,您可以使用 toByteArray() 方法,然后手动找到最重要的 1,然后计算零的数量。这将为您提供整数精度的以 2 为底的对数。

于 2012-08-18T23:27:28.570 回答
1

bit hacks 页面对于这样的事情很有用。

那里的代码在 C 中,但基本思想也适用于 C#。

于 2012-08-18T23:28:05.657 回答
0

如果您可以使用近似值,那么请使用英特尔芯片使用的技巧:将值预先计算为合适大小的数组,然后引用该数组。您可以使数组以任何最小/最大值开始和结束,并且您可以根据需要创建任意数量的中间值以实现所需的精度。

于 2012-08-18T23:28:41.397 回答