Last active
September 25, 2018 22:07
-
-
Save jbruni/3004a783369a60931e2baf644440d129 to your computer and use it in GitHub Desktop.
Math functions suitable for monetary calculations
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
/** | |
* Basic Arithmetic | |
*/ | |
const bind = Function.prototype.bind, | |
liberate = bind.bind(Function.prototype.call), | |
reduce = liberate(Array.prototype.reduce), | |
slice = liberate(Array.prototype.slice); | |
function multiplier(x) { | |
const parts = x.toString().split('.'); | |
if (parts.length < 2) { | |
return 1; | |
} | |
return Math.pow(10, parts[1].length); | |
} | |
function correctionFactor() { | |
return reduce(arguments, function (prev, next) { | |
const mp = multiplier(prev), | |
mn = multiplier(next); | |
return mp > mn ? mp : mn; | |
}, -Infinity); | |
} | |
export function add() { | |
var corrFactor = correctionFactor.apply(null, arguments); | |
function cback(accum, curr, currI, O) { | |
return accum + corrFactor * curr; | |
} | |
return reduce(arguments, cback, 0) / corrFactor; | |
} | |
export function sub() { | |
var corrFactor = correctionFactor.apply(null, arguments), | |
first = arguments[0]; | |
function cback(accum, curr, currI, O) { | |
return accum - corrFactor * curr; | |
} | |
delete arguments[0]; | |
return reduce(arguments, | |
cback, first * corrFactor) / corrFactor; | |
} | |
export function mul() { | |
function cback(accum, curr, currI, O) { | |
var corrFactor = correctionFactor(accum, curr); | |
return (accum * corrFactor) * (curr * corrFactor) / | |
(corrFactor * corrFactor); | |
} | |
return reduce(arguments, cback, 1); | |
} | |
export function div() { | |
function cback(accum, curr, currI, O) { | |
var corrFactor = correctionFactor(accum, curr); | |
return (accum * corrFactor) / (curr * corrFactor); | |
} | |
return reduce(arguments, cback); | |
} |
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
// Taken from https://github.com/guipn/sinful.js | |
void function (bless) { | |
'use strict'; | |
var bind = Function.prototype.bind, | |
liberate = bind.bind(Function.prototype.call), | |
reduce = liberate(Array.prototype.reduce), | |
slice = liberate(Array.prototype.slice); | |
bless = bless || function (thing, name, content) { | |
if (typeof thing[name] !== 'undefined') { | |
throw new Error('Sinful: ' + name + ' is already defined.'); | |
} | |
thing[name] = content; | |
}; | |
function multiplier(x) { | |
var parts = x.toString().split('.'); | |
if (parts.length < 2) { | |
return 1; | |
} | |
return Math.pow(10, parts[1].length); | |
} | |
function correctionFactor() { | |
return reduce(arguments, function (prev, next) { | |
var mp = multiplier(prev), | |
mn = multiplier(next); | |
return mp > mn ? mp : mn; | |
}, -Infinity); | |
} | |
[ | |
[Math, 'add', function () { | |
var corrFactor = correctionFactor.apply(null, arguments); | |
function cback(accum, curr, currI, O) { | |
return accum + corrFactor * curr; | |
} | |
return reduce(arguments, cback, 0) / corrFactor; | |
}], | |
[Math, 'sub', function () { | |
var corrFactor = correctionFactor.apply(null, arguments), | |
first = arguments[0]; | |
function cback(accum, curr, currI, O) { | |
return accum - corrFactor * curr; | |
} | |
delete arguments[0]; | |
return reduce(arguments, | |
cback, first * corrFactor) / corrFactor; | |
}], | |
[Math, 'mul', function () { | |
function cback(accum, curr, currI, O) { | |
var corrFactor = correctionFactor(accum, curr); | |
return (accum * corrFactor) * (curr * corrFactor) / | |
(corrFactor * corrFactor); | |
} | |
return reduce(arguments, cback, 1); | |
}], | |
[Math, 'div', function () { | |
function cback(accum, curr, currI, O) { | |
var corrFactor = correctionFactor(accum, curr); | |
return (accum * corrFactor) / (curr * corrFactor); | |
} | |
return reduce(arguments, cback); | |
}], | |
].forEach(function (blessing) { | |
bless(blessing.shift(), blessing.shift(), blessing.shift()); | |
}); | |
}(); |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
I have removed the wrapping code and the Math prototype changes from the original
sinful.js
code.The result is at
basic-math.js
file.