不能使用 float 和 double 来表示金额等精确的值
不能使用 float 和 double 来表示金额等精确的值
关于面试,金额用什么数据类型?
不是 doube,更不是 float ,而是用 BigDecimal。对于金融项目,对于金额,误差是不能容忍的。那么用什么数据类型才能精确的表示金额?JDK 提供了一个 java.math.BigDecimal 的类,这个类可以表示任意精度的数字。
Java 中 float 的精度为 6-7 位有效数字。double 的精度为 15-16 位,BigDecimal 用来对超过16位有效位的数进行精确的运算
关于 float 和 double 的精度
float:2^23 = 8388608,一共七位尾数,这意味着最多能有 7 位有效数字,但绝对能保证的为6位,也即 float 的精度为 6~7 位有效数字;
double:2^52 = 4503599627370496,一共 16 位,同理,double 的精度为15~16位。
顺带看另一个问题:
float 不是 4 个字节 32 位吗?为啥最大值是 2128-1(3.40E+38)呢?
这和计算机数据存储有关,浮点数在计算机中是按科学计数法来存储的,其中 1 位符号位,8 位指数,23 位尾数。

问题一、出现的计算金额不准确,丢失精度:
看:
public class Test {
public static void main(String[] args) {
double d1 = 11000;
double d2 = 0.35;
// 错误的:3849.9999999999995
System.out.println("错误的:" + d1 * d2);
BigDecimal bigDecimal1 = new BigDecimal(11000);
BigDecimal bigDecimal2 = BigDecimal.valueOf(0.35);
// multiply 乘法;正确的:3850.00
System.out.println("正确的:" + bigDecimal1.multiply(bigDecimal2));
}
}
问题二、数据类型转换时会有问题
public class Test {
public static void main(String[] args) {
long longMaxVal = Long.MAX_VALUE;
double doubleVal = longMaxVal / 1.0;
double clone = doubleVal;
// 参考 Alibaba 《码出高效》, 两浮点数之差小于 diff 任务相等比较改进
float diff = 1e-6f;
System.out.println(doubleVal);
clone += 1000;
System.out.println(clone);
if (Math.abs(clone - doubleVal) < diff) {
// do
System.out.println("两数相等");
} else {
System.out.println("两数不相等");
}
}
}
不能使用 float 和 double 来表示金额等精确的值的更多相关文章
- decimal,float和double的区别
http://www.cnblogs.com/yellowapplemylove/archive/2011/08/23/2150316.html 一直很奇怪C#的预定义数据类型中为什么加了一个deci ...
- C#中对于float,double,decimal的误解(转载)
浮点型 Name CTS Type Description Significant Figures Range (approximate) float System.Single 32-bit sin ...
- decimal与float和double的区别
一直很奇怪C#的预定义数据类型中为什么加了一个decimal,有float和double不就够了吗?今天来挖一挖. 浮点型 Name CTS Type De script ion Significan ...
- 精确计算java中float和double的精度
[本文相关的代码放在github上.地址为:https://github.com/VigourJiang/StructuredFloat] Java中double类型的格式基本遵循IEEE 754标准 ...
- Sql的decimal、float、double类型的区别
三者的区别介绍 float:浮点型,含字节数为4,32bit,数值范围为-3.4E38~3.4E38(7个有效位) double:双精度实型,含字节数为8,64bit数值范围-1.7E308~1.7E ...
- float和double精度问题
System.out.println(new BigDecimal(253.90).doubleValue() * 100);25390.0精度正确 System.out.println(new Bi ...
- 【转载】 C#中float、double以及decimal类型有何不同
在C#语言中,float.double以及decimal类型都可以用来表示小数,但三者还是有一定的不同,有效数字为相比的话,decimal类型的有效数字最大,float类型最小.计算浮点类型的运算,如 ...
- float和double的精度
作者: jillzhang 联系方式:jillzhang@126.com 原网址:http://blog.csdn.net/wuna66320/article/details/1691734 1 范围 ...
- float和double在内存中的存储方式
本文转载于:http://wenku.baidu.com/link?url=ARfMiXVHCwCZJcqfA1gfeVkMOj9RkLlR9fIexbgs9gDdV8rIS48A1_xe1y6YgX ...
随机推荐
- 如何禁止谷歌浏览器隐藏url的www前缀
若要将Chrome浏览器的设置恢复为隐藏HTTP.HTTPS以及WWW前缀,则只需再次进入此页面: chrome://flags/#omnibox-ui-hide-steady-state-url-s ...
- ARTS 第一周打卡
Algorithm : 做一个 leetcode 的算法题 1.只出现一次的数字 给定一个非空整数数组,除了某个元素只出现一次以外,其余每个元素均出现两次.找出那个只出现了一次的元素. 说明: 你的算 ...
- django 模块查询
# 查询轮播图slider_list = Slider.objects.filter(type = constants.SLIDER_TYPE_INDEX) # 查询新闻now_time = date ...
- 数值优化(Numerical Optimization)学习系列-目录
数值优化(Numerical Optimization)学习系列-目录 置顶 2015年12月27日 19:07:11 下一步 阅读数 12291更多 分类专栏: 数值优化 版权声明:本文为博主原 ...
- 【原创】大数据基础之Kudu(4)spark读写kudu
spark2.4.3+kudu1.9 1 批量读 val df = spark.read.format("kudu") .options(Map("kudu.master ...
- 【weixi】微信支付---微信公众号JSAPI支付
一.JSAPI支付 JSAPI支付是用户在微信中打开商户的H5页面,商户在H5页面通过调用微信支付提供的JSAPI接口调起微信支付模块完成支付.应用场景有: ◆ 用户在微信公众账号内进入商家公众号,打 ...
- Qtspim和MIPS的坑
Qtspim和MIPS的坑 数组要么用空格隔开,要么逗号之后再加一个空格 乘法的结果保存在(HI,LO)寄存器中,但是不能直接通过Move得到,必须使用mfhi 和mflo指令 用户输入的数组最后一个 ...
- 使用javascript和jquery获取类方法
1.本质区别 jquery是一个javascript库.jquery是一个基于javascript语言的框架,本质上就是javascript. 2.代码编写的差异 jquery大大简化了JavaScr ...
- asp.net Core 2.0 MVC为Controller或Action添加定制特性实现登录验证
前言:最近在倒腾 微软的新平台 asp.net Core 2.0,在这个过程中有些东西还是存在差异.下面是我在学习过程的一点笔记.有不妥之处,望各位大虾指正! 一.先创建一个控制器继承于Control ...
- linux环境下,springboot jar启动方式
linux环境下,springboot jar启动方式 一.前台启动(ctrl+c会关掉进程) java -jar application.jar 二.后台启动(ctrl+c不会关闭) java -j ...