数据库sickleave/vacationleave列设decimal仍取整,如何获取正确小数?
嘿,我来帮你捋捋这个头疼的问题——明明把sickleave和vacationleave设成decimal类型了,怎么输入1.50最后变成2了?这种情况我碰到过好多次,大概率不是数据库字段本身的问题,而是数据写入环节的类型转换或配置疏漏。咱们一步步排查:
1. 先确认Decimal字段的精度配置
你说已经设成decimal了,但有没有注意到精度参数?比如如果字段是DECIMAL(10,0),后面的0表示小数位数为0,数据库会自动把所有数值四舍五入成整数。
你可以用这条SQL查看字段的具体配置:
DESCRIBE your_table_name;
找到这两个字段的Type列,确保格式是DECIMAL(M,D),且D是你需要的小数位数(比如存1.50的话,D至少要设为2,比如DECIMAL(5,2))。如果之前设的是DECIMAL(10,0),改成DECIMAL(10,2)再试试。
2. 排查应用层的类型处理
这是最常见的原因!很多时候是代码里把数值当成整数类型处理了:
- 比如后端用
int/Integer类型接收前端传的1.50,直接截断或四舍五入成2; - 或者ORM框架(比如MyBatis、Hibernate)映射实体类时,把这两个字段设成了整数类型,没有对应到
BigDecimal(Java)或Decimal(Python)。
举个例子,Java里实体类要这么写:
// 正确:用BigDecimal对应decimal字段 private BigDecimal sickleave; private BigDecimal vacationleave; // 错误:用int会自动转成整数 // private int sickleave;
3. 检查更新语句的参数绑定
有没有可能在执行更新时,参数被当成整数传递了?比如你写了UPDATE your_table SET sickleave = ?,但绑定参数时不小心把1.5转成了整数2。
可以开启数据库的SQL日志(比如MySQL的general_log),看看实际执行的SQL语句里参数值到底是什么。如果日志里显示的是SET sickleave = 2,那问题肯定出在代码的参数处理上。
4. 验证数据库本身的存储能力
先绕开应用层,直接用SQL语句测试:
UPDATE your_table_name SET sickleave = 1.50 WHERE id = 你的测试ID; SELECT sickleave FROM your_table_name WHERE id = 你的测试ID;
如果查询结果是1.50,说明数据库本身没问题,问题全在应用层;如果直接SQL也存成2,那再检查有没有触发器、存储过程或者约束在偷偷修改数值。
内容的提问来源于stack exchange,提问作者Renzo

