This is my attempt to fix the JavaScript toFixed() function...
Any input, ideas, corrections for possible errors are much appreciated!
- Fix floating point inacurracy (example (35.355).toFixed(2) = 35.36, not 35.35)
- No big additional libraries
- Comprehensive function (readable by humans)
- Mimics toFixed / i.e. outputs exactly the same (albeit with correction for floating point inac. or course)
This is my attempt -> Demo below (see console log)
Number.prototype.toFixed = function(fractionDigits) {
var digits = parseInt(fractionDigits) || 0;
var num = Number(this);
if( isNaN(num) ) {
return 'NaN';
}
var sign = num < 0 ? -1 : 1;
if (sign < 0) { num = -num; }
digits = Math.pow(10, digits);
num *= digits;
num = Math.round( Math.round(num * Math.pow(10,12)) / Math.pow(10,12) );
var finalNumber = sign * num / digits;
// add 0 after last decimal number (not 0) for as many as requested (fractionDigits)
// in else case, check if requested digits exceed actual, then add 0 (avoid 10.1 for toFixed(2))
if(fractionDigits > 0 && finalNumber.toString().indexOf('.') == -1){
// check that .00 is present
finalNumber = finalNumber.toString() + '.' + '0'.repeat(fractionDigits);
} else if(fractionDigits > finalNumber.toString().split('.')[1]?.length){
finalNumber = finalNumber.toString() + '0'.repeat((fractionDigits - finalNumber.toString().split('.')[1]?.length));
}
return finalNumber.toString(); // tofixed returns as string always, do the same
}
console.log('(35.355).toFixed(2)', (35.355).toFixed(2));
console.log('(35.1).toFixed(2)', (35.1).toFixed(2));
console.log('(35).toFixed(2)', (35).toFixed(2));
Number.prototype.toFixed = function(fractionDigits) {
//function toFixed(numberInput, fractionDigits){
var digits = parseInt(fractionDigits) || 0;
var num = Number(this);
if( isNaN(num) ) {
return 'NaN';
}
var sign = num < 0 ? -1 : 1;
if (sign < 0) { num = -num; }
digits = Math.pow(10, digits);
num *= digits;
num = Math.round( Math.round(num * Math.pow(10,12)) / Math.pow(10,12) );
var finalNumber = sign * num / digits;
// add 0 after last decimal number (not 0) for as many as requested (fractionDigits)
if(fractionDigits > 0 && finalNumber.toString().indexOf('.') == -1){
// check that .00 is present
finalNumber = finalNumber.toString() + '.' + '0'.repeat(fractionDigits);
} else if(fractionDigits > finalNumber.toString().split('.')[1]?.length){
finalNumber = finalNumber.toString() + '0'.repeat((fractionDigits - finalNumber.toString().split('.')[1]?.length));
}
return finalNumber.toString(); // tofixed returns as string always, do the same
}
console.log('post-fix | (35.355).toFixed(2)', (35.355).toFixed(2));
console.log('post-fix | (35.1).toFixed(2)', (35.1).toFixed(2));
console.log('post-fix | (35).toFixed(2)', (35).toFixed(2));
If it were me, I might have this string manipulation approach:
Note:
toFixed
since it will not be triggered by it so you don't needisNaN
check.Output: