正如这里所描述的,金钱类型似乎是不鼓励的。
我的应用程序需要存储货币,我应该使用哪种数据类型?数字、金钱还是浮动?
正如这里所描述的,金钱类型似乎是不鼓励的。
我的应用程序需要存储货币,我应该使用哪种数据类型?数字、金钱还是浮动?
当前回答
这不是一个直接的答案,而是一个例子,说明为什么浮动不是货币的最佳数据类型。
由于浮点数在内部的表示方式,它更容易出现舍入错误。
在我们自己的十进制系统中,除2和5之外的任何数都会有四舍五入误差,这两个数都是10的因数。在二进制中,它只有2而不是5,所以即使是“干净的”小数,比如0.2(1/5)也有风险。
如果你尝试以下方法,你就会看到这个结果:
select
0.1::float + 0.2::float as floats, -- 0.30000000000000004
0.1::numeric + 0.2::numeric as numerics --- 0.3
;
这就是那种让审计师抓狂的事情。
其他回答
这不是一个直接的答案,而是一个例子,说明为什么浮动不是货币的最佳数据类型。
由于浮点数在内部的表示方式,它更容易出现舍入错误。
在我们自己的十进制系统中,除2和5之外的任何数都会有四舍五入误差,这两个数都是10的因数。在二进制中,它只有2而不是5,所以即使是“干净的”小数,比如0.2(1/5)也有风险。
如果你尝试以下方法,你就会看到这个结果:
select
0.1::float + 0.2::float as floats, -- 0.30000000000000004
0.1::numeric + 0.2::numeric as numerics --- 0.3
;
这就是那种让审计师抓狂的事情。
我个人的建议是十进制,精度根据您的需要。如果你想要存储整数的货币小单位(例如美分),并且在你的编程语言中处理小数有困难,可以选择精度= 0的Decimal。
为了找到所需的精度,你需要考虑以下几点:
Types of currencies you support (they can have different number of decimals). Cryptocurrencies have up to 18 decimals (ETH). The number of decimals can change over time due to inflation. Storing prices of small units of goods (probably as a result of conversion from another currency) or having accumulators (accumulate 10% fee from 1 cent transactions until the sum reaches 1 cent) can require using more decimals than are defined for a currency Storing integer number of minimal units can lead to the need of rescaling values in the future if you need to change the precision. If you use decimals, it's much easier.
注意,您还需要在所使用的编程语言中找到相应的数据类型。
文章中有更多细节和注意事项。
使用BigInt将货币存储为正整数,表示以最小货币单位表示的货币价值(例如,100美分存储$1.00,100存储¥100(日元,一种零十进制货币)。这正是Stripe所做的——它是全球电子商务领域最重要的金融服务公司之一。
来源:参见https://stripe.com/docs/currencies上的“零十进制货币”
我保持所有的货币字段为:
数字(15,6)
使用这么多小数点数位似乎有些过分,但如果你需要处理多种货币,你就需要如此精确的转换。无论我呈现给用户什么,我总是存储到美元。这样,我就可以很容易地转换到任何其他货币,给定当天的汇率。
如果你只做一种货币,最糟糕的是你浪费了一些空间来存储一些0。
数值与强制2单位精度。永远不要使用float或float之类的数据类型来表示货币,因为如果你这样做,当财务报告的底线数字不正确时,人们会不高兴的。
据我所知,货币类型只是由于历史原因而被保留了下来。
举个例子:1伊朗里亚尔等于0.000030美元。如果您使用的小数位数少于5位,那么1个IRR将在转换后四舍五入为0美元。我知道我们在这里是均分的,但我认为在处理金钱问题时,越安全越好。