我解析了大量的json,操纵了一些值,我想把它写出来。 Aeson会将数字解码为科学数字,但是默认情况下,当对数字进行编码时,Scientific在许多情况下都会以科学计数形式显示数字,而Aeson并没有提供我能看到的任何改变方法。

> decode "[\"asdf\", 1, 1.0, 1000000000.1, 0.01]" :: Maybe Value
Just (Array [String "asdf",Number 1.0,Number 1.0,Number 1.0000000001e9,Number 1.0e-2])

encode (Array [String "asdf",Number 1.0,Number 1.0,Number 1.0000000001e9,Number 1.0e-2])
"[\"asdf\",1,1,1.0000000001e9,1.0e-2]"

> encode (Array [String "asdf", Number 1, Number 1.0, Number 1000000000.1, Number 0.01])
"[\"asdf\",1,1,1.0000000001e9,1.0e-2]"

如何用其他语言可以使用的更广泛接受的格式用数字写出我的值(value)?假设我不关心精度损失或整数溢出。科学软件包具有以这种方式格式化数字的方法,而伊森只是碰巧不使用它。
>formatScientific Fixed Nothing (0.01)
"0.01"

>formatScientific Fixed Nothing (1000000000.1)
"1000000000.1"

最佳答案

pretty printer for Aeson(仅从0.8版开始,是最近的版本)具有一个配置选项,可以完全满足您的要求:

Prelude> :m +Data.Aeson Data.Aeson.Encode.Pretty
Prelude Data.Aeson Data.Aeson.Encode.Pretty> encodePretty' (defConfig{confNumFormat=Decimal}) (Array [String "asdf",Number 1.0,Number 1.0,Number 1.0000000001e9,Number 1.0e-2])
"[\n    \"asdf\",\n    1.0,\n    1.0,\n    1000000000.1,\n    0.01\n]"

不幸的是,这台 pretty-print 现在将实际整数输出为1.0而不是1,我认为这比用科学计数法打印小数(这在任何地方都应该可以解决)要严重得多。默认设置也会发生这种情况:
Prelude Data.Aeson Data.Aeson.Encode.Pretty> encodePretty (Array [String "asdf",Number 1.0,Number 1.0,Number 1.0000000001e9,Number 1.0e-2])
"[\n    \"asdf\",\n    1.0,\n    1.0,\n    1.0000000001e9,\n    1.0e-2\n]"

版本0.7.2仍然打印不带小数部分的整数,就像普通的aeson encode那样:
aeson-pretty-0.7.2:Data.Aeson.Encode.Pretty> encodePretty (Array [String "asdf",Number 1.0,Number 1.0,Number 1.0000000001e9,Number 1.0e-2])
"[\n    \"asdf\",\n    1,\n    1,\n    1.0000000001e9,\n    1.0e-2\n]"

我想我会将其归档为错误报告。

请注意,还有一个 Custom NumberFormat选项,它使您可以完全控制数字的显示方式。

关于haskell - 在aeson中,如何在不产生科学计数法的情况下从“值”进行编码?,我们在Stack Overflow上找到一个类似的问题:https://stackoverflow.com/questions/39375641/

10-15 23:24