您可以将javascript中的数字四舍五入到小数点后1个字符(正确四舍五入)吗?
我尝试了 *10, round, /10 但它在 int 的末尾留下了两位小数。
Math.round(n * 10) / 10
确实有效。你的代码是什么?
Math.round(num * 10) / 10
有效,这是一个示例...
var number = 12.3456789
var rounded = Math.round(number * 10) / 10
// rounded is 12.3
如果你希望它有一位小数,即使那是 0,然后添加......
var fixed = rounded.toFixed(1)
// fixed is always to 1 d.p.
// NOTE: .toFixed() returns a string!
// To convert back to number format
parseFloat(number.toFixed(2))
// 12.34
// but that will not retain any trailing zeros
// So, just make sure it is the last step before output,
// and use a number format during calculations!
编辑:添加带有精确功能的圆形...
使用这个原则,作为参考,这里有一个方便的小圆函数,它需要精度......
function round(value, precision) {
var multiplier = Math.pow(10, precision || 0);
return Math.round(value * multiplier) / multiplier;
}
... 用法 ...
round(12345.6789, 2) // 12345.68
round(12345.6789, 1) // 12345.7
... 默认舍入到最接近的整数(精度 0)...
round(12345.6789) // 12346
...并且可用于四舍五入到最接近的 10 或 100 等...
round(12345.6789, -1) // 12350
round(12345.6789, -2) // 12300
...并正确处理负数...
round(-123.45, 1) // -123.4
round(123.45, 1) // 123.5
...并且可以与 toFixed 结合以一致地格式化为字符串...
round(456.7, 2).toFixed(2) // "456.70"
var number = 123.456;
console.log(number.toFixed(1)); // should round to 123.5
toFixed()
有故障 - 我在 Chrome 浏览器中看到它,我在其中调用 toFixed()
,然后转换为字符串,它显示类似于 10.00000000068
的内容 - 很奇怪。虽然无法可靠地重现这一点。
.toFixed()
,因为当您可能需要 Number
时它会返回 String
我投票给 toFixed()
,但是,为了记录,这是另一种使用位移将数字转换为 int 的方法。因此,它总是向零舍入(正数向下舍入,负数向上舍入)。
var rounded = ((num * 10) << 0) * 0.1;
但是,嘿,因为没有函数调用,所以速度很快。 :)
这是使用字符串匹配的一个:
var rounded = (num + '').replace(/(^.*?\d+)(\.\d)?.*/, '$1$2');
我不建议使用字符串变体,只是说。
试试这个:
var original=28.453
// 1.- round "original" to two decimals
var result = Math.round (original * 100) / 100 //returns 28.45
// 2.- round "original" to 1 decimal
var result = Math.round (original * 10) / 10 //returns 28.5
// 3.- round 8.111111 to 3 decimals
var result = Math.round (8.111111 * 1000) / 1000 //returns 8.111
更简单,更容易实现......
有了这个,你可以创建一个函数来做:
function RoundAndFix (n, d) {
var m = Math.pow (10, d);
return Math.round (n * m) / m;
}
函数 RoundAndFix (n, d) { var m = Math.pow (10, d);返回 Math.round (n * m) / m; } console.log (RoundAndFix(8.111111, 3));
编辑:见此How to round using ROUND HALF UP. Rounding mode that most of us were taught in grade school
您可以简单地执行以下操作:
let n = 1.25
let result = Number(n).toFixed(1)
// output string: 1.3
为什么不只是
let myNumber = 213.27321;
+myNumber.toFixed(1); // => 213.3
toFixed:使用定点表示法返回一个表示给定数字的字符串。一元加号 (+):一元加号运算符位于其操作数之前并计算其操作数,但如果尚未转换为数字,则尝试将其转换为数字。
使用 toPrecision 方法:
var a = 1.2345
a.toPrecision(2)
// result "1.2"
12.345.toPrecision( 2 )
是 "12"
。
通常,小数舍入是通过缩放完成的:round(num * p) / p
幼稚的实现
使用以下带有中间数字的函数,您将获得预期的上舍入值,或者有时取决于输入的下舍入值。
此 inconsistency
舍入可能会在客户端代码中引入难以检测的错误。
函数 naiveRound(num, decimalPlaces) { var p = Math.pow(10, decimalPlaces);返回 Math.round(num * p) / p; } console.log( naiveRound(1.245, 2) ); // 1.25 正确(按预期四舍五入) console.log( naiveRound(1.255, 2) ); // 1.25 不正确(应该是 1.26)
更好的实现
通过将数字转换为指数符号中的字符串,正数按预期四舍五入。但是,请注意负数与正数的舍入方式不同。
事实上,它执行的规则基本上等同于 "round half up",您将看到 round(-1.005, 2)
的计算结果为 -1
,即使 round(1.005, 2)
的计算结果为 1.01
。 lodash _.round 方法使用了这种技术。
/** * 向上取整('向正无穷取整') * 使用指数符号来避免浮点问题。 * 负数舍入方式不同于正数。 */ function round(num, decimalPlaces) { num = Math.round(num + "e" + decimalPlaces);返回数字(num +“e”+ -decimalPlaces); } // 测试一半的四舍五入 console.log( round(0.5, 0) ); // 1 console.log( round(-0.5, 0) ); // 0 // 测试边缘案例 console.log( round(1.005, 2) ); // 1.01 console.log( round(2.175, 2) ); // 2.18 console.log( round(5.015, 2) ); // 5.02 console.log( round(-1.005, 2) ); // -1 console.log( round(-2.175, 2) ); // -2.17 console.log( round(-5.015, 2) ); // -5.01
如果您希望在舍入负数时采用通常的行为,则需要在调用 Math.round() 之前将负数转换为正数,然后在返回之前将它们转换回负数。
// Round half away from zero
function round(num, decimalPlaces) {
num = Math.round(Math.abs(num) + "e" + decimalPlaces) * Math.sign(num);
return Number(num + "e" + -decimalPlaces);
}
有一种不同的纯数学技术可以执行舍入到最近(使用 "round half away from zero"),其中在调用舍入函数之前应用 epsilon 校正。
简单地说,我们在四舍五入之前将可能的最小浮点值(= 1.0 ulp;最后一个单位)添加到数字。这将移动到数字之后的下一个可表示值,远离零。
/** * 从零舍入一半(“商业”舍入) * 使用校正来抵消浮点不准确性。 * 对正数和负数对称地工作。 */ function round(num, decimalPlaces) { var p = Math.pow(10, decimalPlaces); var e = Number.EPSILON * num * p;返回 Math.round((num * p) + e) / p; } // 测试一半的四舍五入 console.log( round(0.5, 0) ); // 1 console.log( round(-0.5, 0) ); // -1 // 测试边缘情况 console.log( round(1.005, 2) ); // 1.01 console.log( round(2.175, 2) ); // 2.18 console.log( round(5.015, 2) ); // 5.02 console.log( round(-1.005, 2) ); // -1.01 console.log( round(-2.175, 2) ); // -2.18 console.log(round(-5.015, 2) ); // -5.02
这需要抵消在十进制数编码期间可能出现的隐式 round-off error,特别是在最后一个小数位具有“5”的数字,如 1.005、2.675 和 16.235。实际上,十进制的 1.005
被编码为 64 位二进制浮点的 1.0049999999999999
;而十进制的 1234567.005
被编码为 64 位二进制浮点数的 1234567.0049999998882413
。
值得注意的是,最大二进制 round-off error
取决于 (1) 数字的大小和 (2) 相对机器 epsilon (2^-52)。
var num = 34.7654;
num = Math.round(num * 10) / 10;
console.log(num); // Logs: 34.8
完成最佳答案:
var round = function ( number, precision )
{
precision = precision || 0;
return parseFloat( parseFloat( number ).toFixed( precision ) );
}
输入参数编号可能“不”总是一个数字,在这种情况下 .toFixed 不存在。
接受答案的 ES 6 版本:
function round(value, precision) {
const multiplier = 10 ** (precision || 0);
return Math.round(value * multiplier) / multiplier;
}
如果您的方法不起作用,请发布您的代码。
但是,您可以通过以下方式完成四舍五入任务:
var value = Math.round(234.567*100)/100
会给你234.56
相似地
var value = Math.round(234.567*10)/10
会给234.5
通过这种方式,您可以使用变量代替上面使用的常量。
我做了一个返回数字类型并且仅在需要时才放置小数(没有 0 填充)。
例子:
roundWithMaxPrecision(11.234, 2); //11.23
roundWithMaxPrecision(11.234, 1); //11.2
roundWithMaxPrecision(11.234, 4); //11.23
roundWithMaxPrecision(11.234, -1); //10
roundWithMaxPrecision(4.2, 2); //4.2
roundWithMaxPrecision(4.88, 1); //4.9
编码:
function roundWithMaxPrecision (n, precision) {
const precisionWithPow10 = Math.pow(10, precision);
return Math.round(n * precisionWithPow10) / precisionWithPow10;
}
小角度过滤器,如果有人想要的话:
angular.module('filters').filter('decimalPlace', function() {
return function(num, precision) {
var multiplier = Math.pow(10, precision || 0);
return Math.round(num * multiplier) / multiplier;
};
});
如果通过:
{{model.value| decimalPlace}}
{{model.value| decimalPlace:1}}
{{model.value| decimalPlace:2}}
:)
这似乎在我扔给它的任何东西上都能可靠地工作:
function round(val, multiplesOf) {
var s = 1 / multiplesOf;
var res = Math.ceil(val*s)/s;
res = res < val ? res + multiplesOf: res;
var afterZero = multiplesOf.toString().split(".")[1];
return parseFloat(res.toFixed(afterZero ? afterZero.length : 0));
}
它四舍五入,因此您可能需要根据用例对其进行修改。这应该有效:
console.log(round(10.01, 1)); //outputs 11
console.log(round(10.01, 0.1)); //outputs 10.1
如果您关心适当的四舍五入,那么:
function roundNumericStrings(str , numOfDecPlacesRequired){
var roundFactor = Math.pow(10, numOfDecPlacesRequired);
return (Math.round(parseFloat(str)*roundFactor)/roundFactor).toString(); }
否则,如果您不这样做,那么您已经收到了以前帖子的回复
str.slice(0, -1)
Math.round( num * 10) / 10
不起作用。
例如,1455581777.8-145558160.4
为您提供 1310023617.3999999
。
所以只使用 num.toFixed(1)
我找到了一种避免精度问题的方法:
function badRound (num, precision) {
const x = 10 ** precision;
return Math.round(num * x) / x
}
// badRound(1.005, 2) --> 1
function round (num, precision) {
const x = 10 ** (precision + 1);
const y = 10 ** precision;
return Math.round(Math.round(num * x) / 10) / y
}
// round(1.005, 2) --> 1.01
Math.round( mul/count * 10 ) / 10
Math.round(Math.sqrt(sqD/y) * 10 ) / 10
谢谢
function rnd(v,n=2) {
return Math.round((v+Number.EPSILON)*Math.pow(10,n))/Math.pow(10,n)
}
这个很好地抓住了角落案例
如果您的源代码是打字稿,您可以使用如下函数:
public static ToFixedRounded(decimalNumber: number, fractionDigits: number): number {
var rounded = Math.pow(10, fractionDigits);
return (Math.round(decimalNumber * rounded) / rounded).toFixed(fractionDigits) as unknown as number;
}
const solds = 136780000000;
const number = (solds >= 1000000000 && solds < 1000000000000) ? { divisor: 1000000000, postfix: "B" }: (solds >= 1000000 && solds < 1000000000) ? { divisor: 1000000, postfix: "M" }: (solds >= 1000 && solds < 1000000) ? { divisor: 1000, postfix: "K" }: { divisor: 1, postfix: null };
const floor = Math.floor(solds / number.divisor).toLocaleString();
const firstDecimalIndex = solds.toLocaleString().charAt(floor.length+1);
const final =firstDecimalIndex.match("0")? floor + number.postfix: floor + "." + firstDecimalIndex + number.postfix;
console.log(final);
136780000000 --> 136.7B
1367800 --> 1.3M
1342 --> 1.3K
.toFixed()
时要小心,因为当您可能需要一个数字时它会返回一个字符串。parseFloat
将删除.toFixed()
留下的小数。一般来说,如果你想做数学,最好按照你的第一个例子。如果要在 UI 中显示数字,请使用.toFixed()
。.toFixed()
,因为它可能会针对不同的浏览器返回不同的舍入结果。阅读 this post 了解有关该主题的详细信息!