FastAPI 自动对响应中的小数值进行四舍五入

问题描述 投票:0回答:1

我在基于 FastAPI 的应用程序中使用基于 Pydantic 的响应模型和 Decimal。我想返回精度高达 20 位小数的响应。但序列化后,将15位小数四舍五入为14位。

例如:

Original Decimal    : 328.448267489936666
Decimal in Response : 328.44826748993665

我尝试过设置

getcontext.prec = 15
,但没有效果。

最小可重复示例:

from decimal import getcontent, Decimal
from fastapi import FastAPI
from typing import Dict

app = FastAPI()


@app.get("/")
def read_root()->Dict[str, Decimal]:
    getcontext().prec = 15 
    return {"a": Decimal(328.448267489936666)}

依赖关系: fastapi==0.92.0

uvicorn==0.20.0

pydantic==1.10.5

Python 3.7

python decimal fastapi pydantic
1个回答
0
投票

使用

Decimal(328.448267489936666)
会发生一些精度损失,因为您要将浮点数转换为小数 - 使用
Decimal("328.448267489936666")
将字符串转换为小数,这样您就可以得到精确的
Decimal
,然后:

import decimal
from fastapi import FastAPI
from typing import Dict

app = FastAPI()


@app.get("/")
def read_root() -> Dict[str, decimal.Decimal]:
    decimal.getcontext().prec = 15
    return {"a": decimal.Decimal("328.448267489936666")}


if __name__ == "__main__":
    import uvicorn

    uvicorn.run(app, port=11111)
~ $ curl http://localhost:11111
{"a":"328.448267489936666"}

注意 Decimal 在 JSON 中是如何成为字符串的;这是因为许多 JSON 解码器仅使用浮点数来表示数字内容(至少默认情况下如此),并且也不能相信它是精确的。

© www.soinside.com 2019 - 2024. All rights reserved.