我的一个模型中有一个很大的DecimalField。
class Price(models.Model):
min_value = models.DecimalField(max_digits=50, decimal_places=20)
所以基本上,它的数量很大,可以存储多达20个精度点。
所有值似乎都起作用,而不是零。可以说我使用以下命令将该字段序列化为json对象:
import json
from django.core.serializers.json import DjangoJSONEncoder
price = Price.objects.get(pk=1)
json = json.loads(json.dumps({
"min_value" : price.min_value,
}, cls=DjangoJSONEncoder))
对于大多数值,我以字符串格式获取正确的十进制数字。但是,如果将min_value设置为0,我将得到如下内容:"0E-20"
我很确定它的意思是0.00000000000000000000
,或在该点之后的20个零。但是,我想以通常的格式,或者基本上是这样:"0.00000000000000000000"
。
如何强制DjangoJSONEncoder执行此操作?注意,我确实意识到我可以使用字符串“ 0E-20”轻松地做到这一点,方法是在破折号后加上数字,运行一次for循环多次,并生成仅包含零的字符串。但是,有没有更好,更优雅的解决方案?
答案 0 :(得分:2)
Django的内置JSON编码器仅将Decimal
对象强制转换为字符串,因此故障出在标准库。
>>> from decimal import Decimal
>>> x = Decimal('0.00000000000000000000')
>>> x
Decimal('0E-20')
>>> str(x)
'0E-20'
>>> '{:f}'.format(x)
'0.00000000000000000000'
通过快速测试,似乎可以将小数格式化为浮点数,因此请尝试使用此自定义编码器:
import decimal
from django.core.serializers.json import DjangoJSONEncoder
class CustomJSONEncoder(DjangoJSONEncoder):
def default(self, o):
if isinstance(o, decimal.Decimal):
return '{:f}'.format(o)
return super().default(o)