2015-08-26 34 views
0

我將Float對象的字段轉換爲json。並且價值0.6由Argonaut轉換爲0.6000000238418579。如何糾正?Argonaut.io錯誤的Float轉換

簡單的測試用例來檢查:

import argonaut.Argonaut._ 
import argonaut.EncodeJson 

class Person(val name: Float) 
val person = new Person(0.6f) 
println("#1") 
println(person.name) 
def PersonEncodeJson: EncodeJson[Person] = 
    EncodeJson((p: Person) => ("name" := p.name) ->: jEmptyObject) 
val json = person.asJson(PersonEncodeJson).nospaces 
println("#2") 
println(json) 

控制檯輸出:

#1 
0.6 
#2 
{"name":0.6000000238418579} 
+0

你怎麼知道這是argonaut的問題?你是否傳遞了一個字面'0.6'變成'0.6000000238418579'?大多數數字不能完全由浮點數表示。 – Simon

+0

@Simon我更新了問題以提供證據。 – Lunigorn

回答

2

你必須使用Float之前格式化浮動?既然你關心確切的價值,那看起來並不合適。使用

BigDecimal代替:

import argonaut.Argonaut._ 
import argonaut.EncodeJson 

class Person(val name: BigDecimal) 
val person = new Person(BigDecimal("0.6")) 

def PersonEncodeJson: EncodeJson[Person] = 
    EncodeJson((p: Person) => ("name" := p.name) ->: jEmptyObject) 

person.asJson(PersonEncodeJson).nospaces 
// res0: String = {"name":0.6} 

或者,如果你不能改變Person類,你可以在Float轉換爲String,然後BigDecimal

import argonaut.Argonaut._ 
import argonaut.EncodeJson 

class Person(val name: Float) 
val person = new Person(0.6f) 

def PersonEncodeJson: EncodeJson[Person] = 
    EncodeJson((p: Person) => 
    ("name" := BigDecimal(p.name.toString)) ->: jEmptyObject) 

person.asJson(PersonEncodeJson).nospaces 
// res0: String = {"name":0.6} 
2

處理花車當這種事情是很正常的。

scala> val a = 0.6f 
a: Float = 0.6 

scala> val b: Double = a 
b: Double = 0.6000000238418579 

要確保它不會發生,你可以添加到JSON

def PersonEncodeJson: EncodeJson[Person] = EncodeJson((p: Person) => ("name" := "%1.1f" format p.name) ->: jEmptyObject) 
+0

這是不好的解決方案,因爲我需要'數字'字段類型在json中,而不是'字符串'。但是你指出我的問題是'Float'和'Double'之間的轉換,現在我知道我應該探索的問題。 – Lunigorn

+0

@Lunigorn也許Chris Martins回答(使用BigDecimal)是你需要的嗎? – Simon