Warning: file_get_contents(/data/phpspider/zhask/data//catemap/0/laravel/10.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
JavaScript中的Fast nextafter函数_Javascript_Floating Point - Fatal编程技术网

JavaScript中的Fast nextafter函数

JavaScript中的Fast nextafter函数,javascript,floating-point,Javascript,Floating Point,我试图在JavaScript中遍历所有32位浮点数,以直观地比较多项式求值方法的准确性。为此,我实现了如下所示的代码。不幸的是,这段代码太慢了 有没有办法提高绩效 在C/C++中,等价的代码在我的计算机上运行一分钟多一点,而我却没有耐心去看这个代码需要多长时间 function nextFloat(f) { // Note that this moves away from 0.0 // It will fail at +/- infinity and result in an

我试图在JavaScript中遍历所有32位浮点数,以直观地比较多项式求值方法的准确性。为此,我实现了如下所示的代码。不幸的是,这段代码太慢了

有没有办法提高绩效

在C/C++中,等价的代码在我的计算机上运行一分钟多一点,而我却没有耐心去看这个代码需要多长时间

function nextFloat(f) {
    // Note that this moves away from 0.0
    // It will fail at +/- infinity and result in an NaN
    var bitRepr = floatToBits(f);
    bitRepr++;
    return bitsToFloat(bitRepr);
}

function prevFloat(f) {
    // Note that this moves towards 0.0
    // This will fail at 0.0 and result in an NaN
    var bitRepr = floatToBits(f);
    bitRepr--;
    return bitsToFloat(bitRepr);
}

function floatToBits(f) {
    var buf = new ArrayBuffer(4);
    (new Float32Array(buf))[0] = f;
    return (new Uint32Array(buf))[0];
}

function bitsToFloat(b) {
    var buf = new ArrayBuffer(4);
    (new Uint32Array(buf))[0] = b;
    return (new Float32Array(buf))[0];
}

另一种方法,我认为是使用乘以(1 +ε),虽然我相信有边缘情况,我将需要解决的位级无论如何。< /P> < P>如果你的代码是同步的,你不需要一直调用<代码>新< /代码>,这意味着您可以保留

uint32数组
float32数组
,它们通过相同的缓冲区链接到所有函数,例如

var obj = (function () {
    var int = new Uint32Array(1),
        float = new Float32Array(int.buffer);
    return {
        i2f: function (i) {
            int[0] = i;
            return float[0];
        },
        f2i: function (f) {
            float[0] = f;
            return int[0];
        },
        next: function () {
            int[0] = int[0] + 1;
            return float[0];
        },
        prev: function () {
            int[0] = int[0] - 1;
            return float[0];
        }
    };
}());

这样的方法应该可以工作,并且不需要分配阵列:

function testall(f) {
    var M = Math.pow(2,-126);
    var x;
    for (p = -1; p <= 1; p +=2) {
        for (s = 0; s < 1<<23; s++) {
            // subnormals (including zeros)
            x = p*M*(s/(1<<23));
            f(x);
        }
        for (b = M; b <= 2/M; b *= 2) {
            for (s = 0; s < 1<<23; s++) {
                // normals
                x = p*b*(1+s/(1<<23));
                f(x);
            }
        }
    }
}
功能测试(f){
var M=数学功率(2,-126);
var x;

对于(p=-1;p)我个人不会选择将对象命名为
int
float
。对于任何了解使用这些类型的语言的人来说,这段代码似乎都有误导性。这段代码显著提高了性能(在V8的堆管理中有点让我失望…),但它仍然需要相当长的时间才能运行。在一个测试中,运行所有正浮点数大约需要6分钟。还有其他地方我可以节省一些钱吗?由于函数本身的迭代次数可能相当慢,看看是否有改进,将代码直接放入循环中这不是我的答案我希望,因为我不希望大多数程序员知道浮点数作为整数递增是什么。不过,它确实让我达到了(未优化的)C速度的两倍。不幸的是,我猜不会有更多的收益,但这已经足够了。