基本上我的问题是:为什么我的价值为130.00000000000003而不是130.0?
我只输出了引擎盖下的所有内容,并希望它足够清晰。我知道它很可能是字符串/浮点数导致这个但我不知道如何解决它。
我已经尝试过parseFloat(),parseFloat()。toFixed(1),parseFloat()。round(1)但仍然继续得到.00000000000003。并非总是,但有时候。
代码:
// ... 'cost' will be passed as a parameter to the function
totalBudget = parseFloat(document.getElementById('currentBudget').value);// e.g value ='4'
ni = parseFloat(totalBudget);
cost = (cost).toFixed(1);
alert("totalBudget " + totalBudget + "\nni " + ni + "\ncost " + cost);
ni += parseFloat(cost);
alert("ni " + ni);
alert('\nni= ' + ni + '\ntotalBudget= ' + totalBudget + '\ncost=' + cost);
var playerCost = parseFloat(document.getElementById('playerCost' + vTemp).value);
playerCost = (playerCost).toFixed(1);
alert('playerCost= ' + playerCost);
alert('\nNow will subtract ');
ni -= playerCost;
alert('\nAfter Subtraction');
alert('\nni= ' + ni + '\nplayerCost= ' + playerCost);
alert('-------'+
'\ncurrBudget= '+totalBudget+
'\nnew budget ni= '+ni+
'\nPlayer#:vTemp= '+vTemp+
'\nCurr player cost= '+playerCost+
'\nNew players cost= '+cost +
"\nParseFloat(playerCost)for curr player= "+parseFloat(playerCost));
输出:
// If cost = 7.2 and playerCost= 7.1. Notice all floating values are super fine.
totalBudget 129.8
ni 129.8
cost 7.2
totalBudget 129.8
ni 129.8
cost 7.2
ni= 137
totalBudget= 129.8
cost=7.2
plaerCost= 7.1
Now will subtract
After Subtraction
ni= 129.9
playerCost= 7.1
-------
currBudget= 129.8
new budget ni= 129.9
Player#:vTemp= 8
Curr player cost= 7.1
New players cost= 7.2
ParseFloat(playerCost)for curr player= 7.1
如果不刷新页面,我会在网站上进行其他操作
输出:
// If cost = 7.3 and playerCost= 7.2. Notice floating points are totally not fine.
totalBudget 129.9
ni 129.9
cost 7.3
ni 137.20000000000002
ni= 137.20000000000002
totalBudget= 129.9
cost=7.3
plaerCost= 7.2
Now will subtract
After Subtraction
ni= 130.00000000000003
playerCost= 7.2
-------
currBudget= 129.9
new budget ni= 130.00000000000003
Player#:vTemp= 8
Curr player cost= 7.2
New players cost= 7.3
ParseFloat(playerCost)for curr player= 7.2
然后我会得到"超预算。请改变你的球员!"错误原因130.00000000000003> 130.0
答案 0 :(得分:2)
尝试用任何编程语言中的(二进制)浮点数做“钱数学”注定要达到这样的命运。浮点涉及二进制分数,而不是小数分数,因此不可避免地会引入这样的异常。
请注意toFixed()
将浮点数转换为字符串。它并没有多大帮助。
编辑 - 注释正确地指出浮点格式不一定是二进制浮点格式。我认为旧的IBM大型机(可能是我所知道的当前z系列机器)使用了基数为16的指数和(可能)基数为16的尾数。然而,如今,IEEE-754格式(好的或坏的)非常通用,它是x86机器使用的格式。 GPU(不一定;我认为32位NVidia浮点非常接近)都是IEEE-754,但我所知道的都是二进制浮点系统。 (具体而言,根据语言的定义,JavaScript是二进制浮点数。)
再次编辑 - Eric Postpischil在下面的评论中给我学习: - )
答案 1 :(得分:2)
对此可能有点矫枉过正,但请尝试BigDecimal。浮点不适合精度数学,javascript没有内置的“十进制”类型来处理它。
此外,如果精度不是问题,请尝试使用toPrecision()方法。它只会切断你不需要的部分。
var a = 1.000000000000005;
var b = a.toPrecision(6); //returns a string
var c = parseFloat(b); //returns a number
alert(b); // shows 1.000000;
alert(c); // shows 1;
编辑:其实你应该没事了
function roundFloat(input, prec) {
return parseFloat(input.toFixed(prec));
}
并将其用于需要舍入的数字。
答案 2 :(得分:0)
如果你有一个有效小数位,乘以10,截断为整数并比较:
var budget = 130.00000000000003;
var c1 = Math.round(budget * 10);
var c2 = Math.round(130 * 10);
if (c1 > c2)
do_something;