Last active
June 26, 2021 05:54
-
-
Save imbcmdth/6338194 to your computer and use it in GitHub Desktop.
Fast Approximate Functions for JavaScript based on https://code.google.com/p/fastapprox/
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
var Approx = { | |
fastlog2: (function () { | |
var a = new ArrayBuffer(4), | |
i = new Int32Array(a), | |
f = new Float32Array(a); | |
return function fasterLog2 (number) { | |
f[0] = number; | |
var t = i[0] * 1.1920928955078125e-7; | |
return t - 126.94269504; | |
}; | |
}()), | |
log2: (function () { | |
var a = new ArrayBuffer(8), | |
i = new Int32Array(a), | |
f = new Float32Array(a); | |
return function fastLog2 (number) { | |
f[0] = number; | |
i[1] = (i[0] & 0x007FFFFF) | 0x3f000000; | |
var t = i[0] * 1.1920928955078125e-7; | |
return t - 124.22551499 - 1.498030302 * f[1] - 1.72587999 / (0.3520887068 + f[1]); | |
}; | |
}()), | |
log: function fastLog (number) { | |
return 0.6931471805599453 * Approx.log2(number); | |
}, | |
log10: function fastLog10 (number) { | |
return 0.30102999566398114 * Approx.log2(number); | |
}, | |
pow2: (function () { | |
var a = new ArrayBuffer(4), | |
i = new Int32Array(a), | |
f = new Float32Array(a); | |
return function fastPow2 (number) { | |
var offset = (number < 0) ? 1 : 0, | |
clipNumber = (number < -126) ? -126 : number, | |
w = clipNumber | 0, | |
z = clipNumber - w + offset; | |
i[0] = ( (1 << 23) * (clipNumber + 121.2740575 + 27.7280233 / (4.84252568 - z) - 1.49012907 * z) ); | |
return f[0]; | |
} | |
})(), | |
exp: function fastExp (number) { | |
return Approx.pow2(1.442695040 * number); | |
}, | |
fastpow2: (function () { | |
var a = new ArrayBuffer(4), | |
i = new Int32Array(a), | |
f = new Float32Array(a); | |
return function fasterPow2 (number) { | |
var clipNumber = (number < -126) ? -126 : number; | |
i[0] = ( (1 << 23) * (clipNumber + 126.94269504) ); | |
return f[0]; | |
} | |
}()), | |
fastexp: function fasterExp (number) { | |
return Approx.fastpow2(1.442695040 * number); | |
}, | |
sinh: function fastSinH (number) { | |
return 0.5 * (Approx.exp(number) - Approx.exp(-number)); | |
}, | |
fastsinh: function fasterSinH (number) { | |
return 0.5 * (Approx.fastexp(number) - Approx.fastexp(-number)); | |
}, | |
cosh: function fastCosH (number) { | |
return 0.5 * (Approx.exp(number) + Approx.exp(-number)); | |
}, | |
fastcosh: function fasterCosH (number) { | |
return 0.5 * (Approx.fastexp(number) + Approx.fastexp(-number)); | |
}, | |
tanh: function fastTanH (number) { | |
return -1.0 + 2.0 / (1.0 + Approx.exp(-2.0 * number)); | |
}, | |
fasttanh: function fasterTanH (number) { | |
return -1.0 + 2.0 / (1.0 + Approx.fastexp(-2.0 * number)); | |
}, | |
pi: Math.PI, | |
halfpi: Math.PI / 2, | |
twopi: 2 * Math.PI, | |
invtwopi: 1 / (2 * Math.PI), | |
twooverpi: 2 / Math.PI, | |
fouroverpi: 4 / Math.PI, | |
fouroverpisq: 4 / (Math.PI * Math.PI), | |
halfpiminustwopi: Math.PI / 2 - 2 * Math.PI, | |
fasthalfsin: (function () { | |
var q = 0.78444488374548933, | |
a = new ArrayBuffer(16), | |
i = new Int32Array(a), | |
f = new Float32Array(a); | |
return function fastHalfSin (number) { | |
f[0] = 0.20363937680730309; | |
f[1] = 0.015124940802184233; | |
f[2] = -0.0032225901625579573; | |
f[3] = number; | |
var sign = i[3] & 0x80000000; | |
i[3] = i[3] & 0x7FFFFFFF; | |
var qpprox = Approx.fouroverpi * number - Approx.fouroverpisq * number * f[3]; | |
var qpproxsq = qpprox * qpprox; | |
i[0] |= sign; | |
i[1] |= sign; | |
i[2] ^= sign; | |
return q * qpprox + qpproxsq * (f[0] + qpproxsq * (f[1] + qpproxsq * f[2])); | |
}; | |
}()), | |
fasterhalfsin: (function () { | |
var q = 0.78444488374548933, | |
a = new ArrayBuffer(8), | |
i = new Int32Array(a), | |
f = new Float32Array(a); | |
return function fasterHalfSin (number) { | |
f[0] = 0.22308510060189463; | |
f[1] = number; | |
var sign = i[1] & 0x80000000; | |
i[1] &= 0x7FFFFFFF; | |
var qpprox = Approx.fouroverpi * number - Approx.fouroverpisq * number * f[1]; | |
i[0] |= sign; | |
return qpprox * (q + f[0] * qpprox); | |
} | |
}()), | |
sin: function fastSin (number) { | |
var k = (number * Approx.invtwopi) | 0, | |
half = (number < 0) ? -0.5 : 0.5; | |
return Approx.fasthalfsin((half + k) * Approx.twopi - number); | |
}, | |
fastsin: function fasterSin (number) { | |
var k = (number * Approx.invtwopi) | 0, | |
half = (number < 0) ? -0.5 : 0.5; | |
return Approx.fasterhalfsin((half + k) * Approx.twopi - number); | |
}, | |
fasthalfcos: function fastHalfCos (number) { | |
var offset = (number > Approx.halfpi) ? Approx.halfpiminustwopi : Approx.halfpi; | |
return Approx.fasthalfsin(number + offset); | |
}, | |
fasterhalfcos: (function () { | |
var p = 0.54641335845679634, | |
a = new ArrayBuffer(4), | |
i = new Int32Array(a), | |
f = new Float32Array(a); | |
return function fasterHalfCos (number) { | |
f[0] = number; | |
i[0] &= 0x7FFFFFFF; | |
var qpprox = 1.0 - Approx.twooverpi * f[0]; | |
return qpprox + p * qpprox * (1.0 - qpprox * qpprox); | |
}; | |
}()), | |
cos: function fastCos (number) { | |
return Approx.sin(number + Approx.halfpi); | |
}, | |
fastcos: function fasterCos (number) { | |
return Approx.fastsin(number + Approx.halfpi); | |
}, | |
fasthalftan: function fastHalfTan (number) { | |
return Approx.fasthalfsin(number) / Approx.fasthalfsin(number + Approx.halfpi); | |
}, | |
fasterhalftan: function fasterHalfTan (number) { | |
return Approx.fasterhalfsin(number) / Approx.fasterhalfsin(number); | |
}, | |
tan: function fastTan (number) { | |
var k = (number * Approx.invtwopi) | 0, | |
half = (number < 0) ? -0.5 : 0.5, | |
newNumber = number - (half + k) * Approx.twopi; | |
return Approx.fasthalfsin(newNumber) / Approx.fasthalfcos(newNumber); | |
}, | |
fasttan: function fasterTan (number) { | |
var k = (number * Approx.invtwopi) | 0, | |
half = (number < 0) ? -0.5 : 0.5, | |
newNumber = number - (half + k) * Approx.twopi; | |
return Approx.fasterhalfsin(newNumber) / Approx.fasterhalfcos(newNumber); | |
} | |
}; |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment