Last active
August 29, 2015 13:56
-
-
Save mastermatt/8870098 to your computer and use it in GitHub Desktop.
Revisions
-
Matt R. Wilson revised this gist
Feb 7, 2014 . 1 changed file with 1 addition and 2 deletions.There are no files selected for viewing
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 charactersOriginal file line number Diff line number Diff line change @@ -1,4 +1,3 @@ /** * Returns the value of a float rounded using the number of decimal points provided as precision. * @@ -39,7 +38,7 @@ Math.precisionRound = function( number, precision ) { return NaN; } // In case the number is already in scientific when casted to string, split off the exponent eSplit = ("" + castNumber).split( "e" ); // Increase the exponent by the given precision and create a scientific notion string -
Matt R. Wilson created this gist
Feb 7, 2014 .There are no files selected for viewing
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 charactersOriginal file line number Diff line number Diff line change @@ -0,0 +1,56 @@ /** * Returns the value of a float rounded using the number of decimal points provided as precision. * * Fixes binary rounding issues eg. Math.round(1.005 * 100) / 100 === 1 that present * problems for accounting and finance-related software. * * The normal technique for rounding with decimals is to multiply the number by the log10 of the * precision, round then divide by the same log eg. for 2 decimal points `round(num * 100) / 100`. * The binary rounding issue, however, causes this: 1.005 * 100 === 100.49999999999999. * * This method plays on the use of converting scientific notation to a number, * eg 1.005e2 === 100.5 so casting: `round(num + "e2") + "e-2"` to a number will result * in the desired result. * * @param {number} number The value to round * @param {int} precision The optional number of decimal digits to round to * * @returns {number} The adjusted value * * Based on MDN function * https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/Math/round */ Math.precisionRound = function( number, precision ) { "use strict"; var nativeRound = Math.round, castNumber = +number, castPrecision = +precision, scaledNumber, eSplit, eString; // If the exp is undefined or zero, just use native rounding if( typeof precision === "undefined" || 0 === castPrecision ) { return nativeRound( number ); } // If the value is not a number or the exp is not an integer... if( isNaN( castNumber ) || !(typeof castPrecision === "number" && 0 === castPrecision % 1) ) { return NaN; } // In case the number is already in scientific when casted to string, eSplit off the exponent eSplit = ("" + castNumber).split( "e" ); // Increase the exponent by the given precision and create a scientific notion string eString = (eSplit[0] + "e" + (eSplit[1] ? (+eSplit[1] + castPrecision) : castPrecision)); // Cast to number and round scaledNumber = nativeRound( +eString ); // Do the same as before, backwards eSplit = ("" + scaledNumber).split( "e" ); eString = (eSplit[0] + "e" + (eSplit[1] ? (+eSplit[1] - castPrecision) : -castPrecision)); return +eString; };