2013-05-31 50 views
0

我有一個電子商務網站與數字產品(沒有庫存,只有報告功能)。mongoDB數學運算後奇怪的結果

,有時我得到與客戶怪異的結果賬戶餘額:

例如客戶在他的餘額30和購買29.95後,我在管理面板中看到他的餘額是0.050000000000001而不是0.05預期。

或有時我看到520.949999999999而不是520.95

這是怎麼發生的?

網站上的PHP運行,並與蒙戈交互雖然YiiMongoDbSuite

+0

它可能與http://stackoverflow.com/questions/588004/is-javascripts-floating-point-math-broken – Orangepill

+0

相關不,如果他不使用JS插入然後是不相關的,你格式化數字,然後重新保存它們?如果不是,那麼其實是原因;你需要告訴PHP你想如何保存它們 – Sammaye

+0

我很困惑yii和yui。 – Orangepill

回答

0

採用雙層或漂浮,不建議用於任何形式的貨幣數學在需要精確的計算是至關重要的。 This question詳細介紹了該主題。更好的選擇是用整數跟蹤這些值,其中1是貨幣的最小單位(在這種情況下爲分),並從那裏開始工作。

取決於你如何做數學題浮動點(節省精確值,相減的結果,或使用$inc運營商),你可能有不同的結果結束了:

> db.foo.insert({ _id: 'value', x: 0.05 }) 
> db.foo.insert({ _id: 'subtraction', x: 30 - 29.95 }) 
> db.foo.insert({ _id: 'decrement', x: 30 }) 
> db.foo.update({ _id: 'decrement' }, { $inc: { x: -29.95 }}) 
> db.foo.find() 
{ "_id" : "value", "x" : 0.05 } 
{ "_id" : "subtraction", "x" : 0.05000000000000071 } 
{ "_id" : "decrement", "x" : 0.05000000000000071 } 

如果你已經開始使用浮點數並在PHP中進行數學運算(即在更新查詢中不使用$inc),請考慮使用round()以設置精度,這應該會產生類似於上面第一個示例的結果。 number_format()可以顯示,但在更新文檔時請注意不要使用它,因爲它返回一個字符串。