详解java的四舍五入与保留位
JavaDecimalFormat保留小数位及四舍五入的陷阱介绍
JavaDecimalFormat保留⼩数位及四舍五⼊的陷阱介绍⽬录需求代码实现发现问题RoundingMode.HALF_EVEN错误的代码测试RoundingMode.HALF_EVEN正确的代码测试RoundingMode.HALF_EVEN结论需求业务需要导出的Excel的数字内容保留两位⼩数,并且四舍五⼊代码实现百度⼀圈所抄袭的代码DecimalFormat dfScale2 = new DecimalFormat("###.##");dfScale2.format(1.125D);发现问题导出数据很诡异.不是所有数据都是如所想的四舍五⼊.经过排查最终发现是RoundingMode的问题,应该使⽤HALF_UP,DecimalFormat 默认使⽤的是HALF_EVENDecimalFormat dfScale2 = new DecimalFormat("###.##");System.out.println("dfScale2.getRoundingMode()=" + dfScale2.getRoundingMode());//输出结果dfScale2.getRoundingMode()=HALF_EVEN//RoundingMode.HALF_EVEN想了解HALF_EVEN,HALF_EVEN 被舍位是5(如保留两位⼩数的2.115),后⾯还有⾮0值进1(如保留两位⼩数的2.11500001 格式化为2.12),5后⾯没有数字或者都是0时,前⾯是偶数则舍,是奇数则进1,⽬标是让被舍前⼀位变为偶数.CEILING 向更⼤的值靠近Rounding mode to round towards positive infinity.DOWN向下取整Rounding mode to round towards zero.FLOOR 向更⼩的值靠近Rounding mode to round towards negative infinity.HALF_DOWN 五舍六⼊Rounding mode to round towards “nearest neighbor” unless both neighbors are equidistant, in which case round down.HALF_EVENRounding mode to round towards the “nearest neighbor” unless both neighbors are equidistant, in which case, round towards the even neighbor.HALF_UP 四舍五⼊Rounding mode to round towards “nearest neighbor” unless both neighbors are equidistant, in which case round up.UNNECESSARY 设置这个模式,对于精确值格式化会抛出异常Rounding mode to assert that the requested operation has an exact result, hence no rounding is necessary.UP 向远离数字0进⾏进位.Rounding mode to round away from zero.错误的代码测试RoundingMode.HALF_EVEN为了更好的理解HALF_EVEN,写了些测试代码但是发现⾃⼰更迷惘了…搞不清楚到底HALF_EVEN是什么机制进舍…输出结果的尾数很不规律.import java.math.BigDecimal;import java.math.RoundingMode;import java.text.DecimalFormat;import java.util.*;public class LocalTest {//定义⼀个保留两位⼩数格式的 DecimalFormat 的变量 dfScale2@Testpublic void testDecimalFormat() {DecimalFormat dfScale2 = new DecimalFormat("###.##");System.out.println("dfScale2.getRoundingMode()=" + dfScale2.getRoundingMode());System.out.println("dfScale2.format(1.125D)=" + dfScale2.format(1.125D));System.out.println("dfScale2.format(1.135D)=" + dfScale2.format(1.135D));System.out.println("dfScale2.format(1.145D)=" + dfScale2.format(1.145D));System.out.println("dfScale2.format(1.225D)=" + dfScale2.format(1.225D));System.out.println("dfScale2.format(1.235D)=" + dfScale2.format(1.235D));System.out.println("dfScale2.format(1.245D)=" + dfScale2.format(1.245D));System.out.println();System.out.println("dfScale2.format(2.125D)=" + dfScale2.format(2.125D));System.out.println("dfScale2.format(2.135D)=" + dfScale2.format(2.135D));System.out.println("dfScale2.format(2.145D)=" + dfScale2.format(2.145D));System.out.println("dfScale2.format(2.225D)=" + dfScale2.format(2.225D));System.out.println("dfScale2.format(2.235D)=" + dfScale2.format(2.235D));System.out.println("dfScale2.format(2.245D)=" + dfScale2.format(2.245D));System.out.println();System.out.println("dfScale2.format(3.125D)=" + dfScale2.format(3.125D));System.out.println("dfScale2.format(3.135D)=" + dfScale2.format(3.135D));System.out.println("dfScale2.format(3.145D)=" + dfScale2.format(3.145D));System.out.println("dfScale2.format(3.225D)=" + dfScale2.format(3.225D));System.out.println("dfScale2.format(3.235D)=" + dfScale2.format(3.235D));System.out.println("dfScale2.format(3.245D)=" + dfScale2.format(3.245D));System.out.println();System.out.println("dfScale2.format(4.125D)=" + dfScale2.format(4.125D));System.out.println("dfScale2.format(4.135D)=" + dfScale2.format(4.135D));System.out.println("dfScale2.format(4.145D)=" + dfScale2.format(4.145D));System.out.println("dfScale2.format(4.225D)=" + dfScale2.format(4.225D));System.out.println("dfScale2.format(4.235D)=" + dfScale2.format(4.235D));System.out.println("dfScale2.format(4.245D)=" + dfScale2.format(4.245D));}}dfScale2.getRoundingMode()=HALF_EVENdfScale2.format(1.125D)=1.12dfScale2.format(1.135D)=1.14dfScale2.format(1.145D)=1.15dfScale2.format(1.225D)=1.23dfScale2.format(1.235D)=1.24dfScale2.format(1.245D)=1.25dfScale2.format(2.125D)=2.12dfScale2.format(2.135D)=2.13dfScale2.format(2.145D)=2.15dfScale2.format(2.225D)=2.23dfScale2.format(2.235D)=2.23dfScale2.format(2.245D)=2.25dfScale2.format(3.125D)=3.12dfScale2.format(3.135D)=3.13dfScale2.format(3.145D)=3.15dfScale2.format(3.225D)=3.23dfScale2.format(3.235D)=3.23dfScale2.format(3.245D)=3.25dfScale2.format(4.125D)=4.12dfScale2.format(4.135D)=4.13dfScale2.format(4.145D)=4.14dfScale2.format(4.225D)=4.22dfScale2.format(4.235D)=4.24dfScale2.format(4.245D)=4.25正确的代码测试RoundingMode.HALF_EVEN突然发现⾃⼰忽略了⼀个事情,测试的参数都是⽤的double类型.想起来double类型不精准.但是侥幸⼼理以及知识不牢靠以为 3位⼩数应该影响不⼤吧.改了下代码,把参数改为BigDecimal类型使⽤BigDecimal时,参数尽量传⼊字符串,要⽐传⼊double精准.new BigDecimal("1.125")@Testpublic void testDecimalFormat() {DecimalFormat dfScale2 = new DecimalFormat("###.##");dfScale2.setRoundingMode(RoundingMode.HALF_EVEN);System.out.println("dfScale2.getRoundingMode()=" + dfScale2.getRoundingMode());System.out.println("dfScale2.format(new BigDecimal(\"1.1251\"))=" + dfScale2.format(new BigDecimal("1.1251")));System.out.println("dfScale2.format(new BigDecimal(\"1.1351\"))=" + dfScale2.format(new BigDecimal("1.1351")));System.out.println("dfScale2.format(new BigDecimal(\"1.1451\"))=" + dfScale2.format(new BigDecimal("1.1451")));System.out.println("dfScale2.format(new BigDecimal(\"1.2250\"))=" + dfScale2.format(new BigDecimal("1.2250")));System.out.println("dfScale2.format(new BigDecimal(\"1.2350\"))=" + dfScale2.format(new BigDecimal("1.2350")));System.out.println("dfScale2.format(new BigDecimal(\"1.2450\"))=" + dfScale2.format(new BigDecimal("1.2450")));System.out.println("dfScale2.format(new BigDecimal(\"1.22501\"))=" + dfScale2.format(new BigDecimal("1.22501")));System.out.println("dfScale2.format(new BigDecimal(\"1.23505\"))=" + dfScale2.format(new BigDecimal("1.23505")));System.out.println("dfScale2.format(new BigDecimal(\"1.24508\"))=" + dfScale2.format(new BigDecimal("1.24508")));dfScale2.getRoundingMode()=HALF_EVENdfScale2.format(new BigDecimal("1.1251"))=1.13dfScale2.format(new BigDecimal("1.1351"))=1.14dfScale2.format(new BigDecimal("1.1451"))=1.15dfScale2.format(new BigDecimal("1.2250"))=1.22dfScale2.format(new BigDecimal("1.2350"))=1.24dfScale2.format(new BigDecimal("1.2450"))=1.24dfScale2.format(new BigDecimal("1.22501"))=1.23dfScale2.format(new BigDecimal("1.23505"))=1.24dfScale2.format(new BigDecimal("1.24508"))=1.25结论1、警觉doulbe的不精确所引起RoundingMode结果不稳定的问题,即使是四舍五⼊的模式,对double类型参数使⽤也会有不满⾜预期的情况.2、使⽤数字格式化时,要注意默认RoundingMode模式是否是⾃⼰需要的.如果不是记得⼿动设置下.以上为个⼈经验,希望能给⼤家⼀个参考,也希望⼤家多多⽀持。
JAVA数值四舍五入
Math.ceil求最小的整数但不小于本身.
Math.round求本身的四舍五入。
Math.floor求最大的整数但不大于本身.
问题
我要进行四舍五入或取近似值.
解决办法
用 Math.round( ) 进行四舍五入, Math.floor( ) 和 Math.ceil( ) 进行上下近似值。NumberUtilities.round( ) 方法可自定义取值。
讨论
很多情况我们需要得到整数部分而不是带有小数的浮点数。比如计算出结果为 3.9999999 ,期望的结果应该是4.0。
Math.round( ) 方法进行四舍五入计算:
trace(Math.round(204.499)); // 显示: 204
trace(Math.round(401.5)); // 显示: 402
trace(NumberUtilities.round(123.456, 6)); // Displays: 126
trace(NumberUtilities.round(123.456, .01)); // Displays: 123.46
number :要舍入的数字
roundToInterval :间隔值
NumberUtilities 类在 ascb.util 包中。
imported ascb.util.NumberUtilities导入
trace(NumberUtilities.round(Math.PI)); // Displays: 3
trace(NumberUtilities.round(Math.PI, .01)); // Displays: 3.14
java roundingmode方法使用说明
java roundingmode方法使用说明Java中的roundingMode方法是用于设置BigDecimal对象进行小数点舍入操作的模式。
该方法属于BigDecimal类的一部分,可帮助我们更精确地处理浮点数。
在Java中,浮点数的舍入是指将一个浮点数按照一定的规则进行近似处理,保留指定的小数位数。
roundingMode方法可以设置不同的舍入模式,以满足不同的需求。
roundingMode方法接受一个RoundingMode枚举值作为参数。
RoundingMode枚举定义了七种舍入模式,分别是:1. UP(向上舍入):在舍入过程中,如果需要舍入的部分大于0,则将结果向上舍入,即使其小数部分小于一半。
2. DOWN(向下舍入):在舍入过程中,如果需要舍入的部分小于0,则将结果向下舍入,即使其小数部分大于一半。
3. CEILING(向正无穷方向舍入):将结果舍入为大于或等于当前值的最小整数。
4. FLOOR(向负无穷方向舍入):将结果舍入为小于或等于当前值的最大整数。
5. HALF_UP(四舍五入):在舍入过程中,如果需要舍入的部分大于等于0.5,则将结果向上舍入,否则向下舍入。
6. HALF_DOWN(五舍六入):在舍入过程中,如果需要舍入的部分大于0.5,则将结果向上舍入,否则向下舍入。
7. HALF_EVEN(银行家舍入法):在舍入过程中,如果需要舍入的部分恰好等于0.5,则将结果向最接近的偶数方向舍入。
以下是一个示例代码,演示了如何使用roundingMode方法:```javaimport java.math.BigDecimal;import java.math.RoundingMode;public class RoundingModeExample {public static void main(String[] args) {BigDecimal number = new BigDecimal("3.14159");// 设置舍入模式为四舍五入BigDecimal roundedNumber = number.setScale(2, RoundingMode.HALF_UP);System.out.println("Rounded Number: " + roundedNumber);}}```在上面的示例中,我们创建了一个BigDecimal对象number,并将其值设置为"3.14159"。
JAVA大数类—基础操作(加减乘除、取模、四舍五入、设置保留位数)
JAVA⼤数类—基础操作(加减乘除、取模、四舍五⼊、设置保留位数)当基础数据类型长度⽆法满⾜需求时可以使⽤⼤数类 构造⽅法接受字符串为参数1 BigInteger bInt = new BigInteger("123123");2 BigDecimal bDouble = new BigDecimal("123123.123123124"); 基础操作(取模使⽤divideAndRemainder⽅法,返回的数组第⼆个元素为余数): BigDecimal在做除法时必须设定传⼊精度(保留多少位⼩数),否则会出现异常:ng.ArithmeticException: Non-terminating decimal expansion; no exact representable decimal result。
除法还有两个接受不同数量参数的⽅法: 接受两个参数的⽅法: @param divisor value by which this {@code BigDecimal} is to be divided. 传⼊除数 @param roundingMode rounding mode to apply. 传⼊round的模式 三个参数的⽅法: @param divisor value by which this {@code BigDecimal} is to be divided. 传⼊除数 @param scale scale of the {@code BigDecimal} quotient to be returned. 传⼊精度 @param roundingMode rounding mode to apply. 传⼊round的模式 round模式为⼩数取舍模式: BigDecimal.ROUND_UP:最后⼀位如果⼤于0,则向前进⼀位,正负数都如此。
java中double变量保留小数问题
做java项目的时候可能经常会遇到double类型变量保留小数的问题,下面便把我的经验做个简短的总结:java中double类型变量保留小数问题大体分两种情况:(一):小数点后面位数过长,四舍五入保留指定位数:可以用以下代码实现:public class TestDemo {public static void main(String[] args) {double a=15.32743859;double b=Math.round(a*10000)/10000.0000;//保留四位小数System.out.println(b);}}想保留n位小数,就Math.round(a*10的n次方)/10的n次方.n个0。
(二):如果小数点后末位为0,myeclipse中不予显示,如double a=15.80;System.out.print(a);则在控制台中输出的结果是15.8。
而我们有时候希望把百分位的0也显示出来,比如说显示商品价格,一般是显示两位小数,如果商品价格是15.8,也显示为15.80,如果商品价格是15,也显示为15.00,这种情况,用(一)中的方法便无法实现了,那应该如何实现呢?请看下面代码:import java.text.DecimalFormat;public class TestDemo {public static void main(String[] args) {DecimalFormat df =new DecimalFormat("#####0.00");double a=15;System.out.println(df.format(a));}}这样,即使在我们的double类型变量是15,显示出来的也是15.00。
当然,我们希望显示多少位就在"#####0.00"的点后面去控制0的个数便可以。
如果是"#####0"的话,那我们的double变量无论是15.0或是15.00都能显示成15,而如果我们的double变量是15.60,则显示为16,即这种方法也可以实现四舍五入。
Java浮点数的精确计算及四舍五入的设置
Java浮点数的精确计算及四舍五入的设置四舍五入的设置(1)、浮点数精确计算项目中一直存在一个问题,就是每次报表统计的物资金额和实际的金额要差那么几分钱,和实际金额不一致,让客户觉得总是不那么舒服,原因是因为我们使用java的浮点类型double 来定义物资金额,并且在报表统计中我们经常要进行一些运算,但Java中浮点数(double、float)的计算是非精确计算,请看下面一个例子:System.out.println(0.05 + 0.01);System.out.println(1.0 - 0.42);System.out.println(4.015 * 100);System.out.println(123.3 / 100);你的期望输出是什么?可实际的输出确实这样的:0.0600000000000000050.5800000000000001401.499999999999941.2329999999999999这个问题就非常严重了,如果你有123.3元要购买商品,而计算机却认为你只有123.29999999999999元,钱不够,计算机拒绝交易。
(2)、四舍五入是否可以四舍五入呢?当然可以,习惯上我们本能就会这样考虑,但四舍五入意味着误差,商业运算中可能意味着错误,同时Java中也没有提供保留指定位数的四舍五入方法,只提供了一个Math.round(double d)和Math.round(float f)的方法,分别返回长整型和整型值。
round 方法不能设置保留几位小数,我们只能象这样(保留两位):public double round(double value){return Math.round( value * 100 ) / 100.0;}但非常不幸的是,上面的代码并不能正常工作,给这个方法传入4.015它将返回4.01而不是4.02,如我们在上面看到的4.015 * 100 = 401.49999999999994因此如果我们要做到精确的四舍五入,这种方法不能满足我们的要求。
java中的取整与四舍五入方法实例
java中的取整与四舍五⼊⽅法实例⼀.java中取整数的⽅式1.直接使⽤强制转换public static void roundOne(){System.out.println("正数:(int)10.12 = " + (int)10.12);System.out.println("负数:(int)-10.12 = " + (int)-10.12);System.out.println("---------------------------------");System.out.println("正数:(int)1011111111111111111111.12 = " + (int)1011111111111111111111.12);System.out.println("负数:(int)-1011111111111111111111.12 = " + (int)-1011111111111111111111.12);}直接⽤强制转换的⽅式将浮点型数据转换为整型时,直接去掉⼩数点后部分的精度,取整数部分;直接强制取整有精度风险,⼀⽅⾯是⼩数位损失,另⼀⽅⾯当浮点型数字超过整型数字最⼤值时,会发⽣溢出。
实际⼯程中,如果这两种因素都不会对⼯程产⽣影响,可以使⽤,否则不建议使⽤。
2.java中提供的取整的函数java中提供了三种取整的函数:(1).Math.ceil(double num);(2).Math.floor(double num);(3).Math.round(double num);public static void roundTwo(){System.out.println("正数:Math.ceil(10.12) = " + Math.ceil(10.12));System.out.println("负数:Math.ceil(-10.12) = " + Math.ceil(-10.12));System.out.println("正数:Math.ceil(101111111111111111111.12) = " + Math.ceil(101111111111111111111.12));System.out.println("负数:Math.ceil(-101111111111111111111.12) = " + Math.ceil(-101111111111111111111.12));System.out.println("---------------------------------");System.out.println("正数:Math.floor(10.12) = " + Math.floor(10.12));System.out.println("负数:Math.floor(-10.12) = " + Math.floor(-10.12));System.out.println("正数:Math.floor(101111111111111111111.12) = " + Math.floor(101111111111111111111.12));System.out.println("负数:Math.floor(-101111111111111111111.12) = " + Math.floor(-101111111111111111111.12));}Math.ceil(double num);函数是取浮点数的天花板数,即不⼩于num的最⼩整数;Math.floor(double num)函数是取地板数,即不⼤于num的最⼤整数。
java 四舍五入注解
java 四舍五入注解在Java中,如果你想对一个浮点数进行四舍五入,你可以使用Math.round()方法。
下面是一个简单的示例:java复制代码double d = 12.3456;int roundedValue = Math.round(d * 100); // 对d进行四舍五入到最接近的整数,然后除以100System.out.println(roundedValue); // 输出:1235如果你想对一个浮点数进行四舍五入到特定的小数位数,你可以使用DecimalFormat类:java复制代码double d = 12.3456;DecimalFormat df = new DecimalFormat("#.##"); // 设置小数位数为2String formattedValue = df.format(d);System.out.println(formattedValue); // 输出:12.35如果你想对一个浮点数进行四舍五入并保留指定的小数位数,你可以使用DecimalFormat 类结合Math.round()方法:java复制代码double d = 12.3456;DecimalFormat df = new DecimalFormat("#.##"); // 设置小数位数为2String formattedValue = df.format(Math.round(d * 100) / 100.0); // 对d进行四舍五入到最接近的0.01,然后除以100.0System.out.println(formattedValue); // 输出:12.35请注意,这些方法都是基于标准的四舍五入规则,即“round half to nearest even”(四舍六入五留双)。
如果你想使用不同的舍入规则,可能需要实现自定义的舍入方法。
java四舍五入算法
java四舍五入算法一、什么是四舍五入算法?四舍五入算法是一种常见的数值处理方法,它将一个数值按照一定规则进行舍入取整。
在Java编程中,四舍五入算法可以通过Math.round()方法实现。
二、Math.round()方法的使用1. Math.round()方法的语法格式Math.round(double num)其中,num为需要进行四舍五入操作的数值。
2. Math.round()方法的返回值类型Math.round()方法返回一个long类型的整数,表示经过四舍五入后得到的结果。
3. Math.round()方法的作用Math.round()方法可以将一个double类型的数值进行四舍五入操作,并返回一个整型结果。
三、Java中四舍五入算法实现原理在Java中,四舍五入算法是基于IEEE 754标准所定义的浮点运算规范实现的。
该规范定义了浮点运算中各种情况下如何处理精度和溢出等问题。
具体来说,在Java中进行四舍五入操作时,会根据以下规则来确定最终结果:1. 如果要保留小数位数为0,则直接对原数值进行取整操作即可;2. 如果要保留小数位数不为0,则先将原数值乘以10^n(n为要保留的小数位数),然后对结果进行取整操作,并再次除以10^n即可。
四、Java中四舍五入算法的应用场景在实际编程中,Java中的四舍五入算法可以应用于以下场景:1. 金融计算:在金融计算中,需要对金额进行精确计算和处理,而四舍五入算法可以确保计算结果的精度和准确性;2. 统计学分析:在统计学分析中,需要对数据进行精确处理和分析,而四舍五入算法可以使数据更加准确和可靠;3. 数据库操作:在数据库操作中,需要对数值进行精确处理和存储,而四舍五入算法可以保证数据的完整性和正确性。
五、Java中四舍五入算法的注意事项在使用Java中的四舍五入算法时,需要注意以下问题:1. 精度问题:由于浮点数本身就存在精度问题,在进行四舍五入操作时可能会出现误差;2. 取整方式:在进行取整操作时,应该根据具体需求选择合适的取整方式(如向上取整、向下取整等);3. 代码规范:编写代码时应该遵循良好的代码规范,以提高代码可读性和可维护性。
java整数相除保留一位小数的方法
在 Java 中,如果你想进行整数相除并保留一位小数,你可以通过将其中一个操作数转换为浮点数或使用除法后手动保留一位小数的方式实现。
以下是两种常见的方法:
方法一:将其中一个操作数转换为浮点数
在这个例子中,将numerator强制类型转换为double,然后进行除法运算,最后使用printf方法将结果格式化为一个小数点后一位的字符串输出。
方法二:手动保留一位小数
在这个例子中,同样是将numerator强制类型转换为double,进行除法运算,然后使用Math.round方法将结果乘以10,四舍五入到最近的整数,再除以10.0,以保留一位小数。
最后将结果输出。
这两种方法都可以达到将整数相除并保留一位小数的效果,具体选择哪种方法取决于你的需求和代码的上下文。
java中round方法
java中round方法
Java中的round方法是用于对浮点数进行四舍五入的方法。
该方法可以接受一个float或double类型的参数,并返回一个long型的整数。
round方法采用的是最近舍入法,即对于小数点后的第一位,如果是小于5的数,就舍去;如果是大于等于5的数,就进位。
例如,round(2.4)的结果为2,round(2.5)的结果为3。
在使用round方法时,需要注意以下几点:
1.如果参数为NaN或正负无穷大,则返回结果为0。
2.如果参数为一个整数,例如
3.0或-
4.0,则直接返回该整数的long型值。
3.如果参数为一个带小数的数,例如3.14或-
4.56,则按照最近舍入法进行四舍五入,并返回long型的整数值。
4.如果参数为一个非常大或非常小的数,可能会出现精度误差,导致结果不准确。
因此,在使用round方法时,需要根据具体情况选择合适的参数类型,并注意参数的范围和精度问题。
- 1 -。
java取整和java四舍五入方法
java取整和java四舍五⼊⽅法import java.math.BigDecimal;import java.text.DecimalFormat;public class TestGetInt{public static void main(String[] args){double i=2, j=2.1, k=2.5, m=2.9;System.out.println("舍掉⼩数取整:Math.floor(2)=" + (int)Math.floor(i));System.out.println("舍掉⼩数取整:Math.floor(2.1)=" + (int)Math.floor(j));System.out.println("舍掉⼩数取整:Math.floor(2.5)=" + (int)Math.floor(k));System.out.println("舍掉⼩数取整:Math.floor(2.9)=" + (int)Math.floor(m));/* 这段被注释的代码不能正确的实现四舍五⼊取整System.out.println("四舍五⼊取整:Math.rint(2)=" + (int)Math.rint(i));System.out.println("四舍五⼊取整:Math.rint(2.1)=" + (int)Math.rint(j));System.out.println("四舍五⼊取整:Math.rint(2.5)=" + (int)Math.rint(k));System.out.println("四舍五⼊取整:Math.rint(2.9)=" + (int)Math.rint(m));System.out.println("四舍五⼊取整:(2)=" + new DecimalFormat("0").format(i));System.out.println("四舍五⼊取整:(2.1)=" + new DecimalFormat("0").format(i));System.out.println("四舍五⼊取整:(2.5)=" + new DecimalFormat("0").format(i));System.out.println("四舍五⼊取整:(2.9)=" + new DecimalFormat("0").format(i));*/System.out.println("四舍五⼊取整:(2)=" + new BigDecimal("2").setScale(0, BigDecimal.ROUND_HALF_UP));System.out.println("四舍五⼊取整:(2.1)=" + new BigDecimal("2.1").setScale(0, BigDecimal.ROUND_HALF_UP)); System.out.println("四舍五⼊取整:(2.5)=" + new BigDecimal("2.5").setScale(0, BigDecimal.ROUND_HALF_UP)); System.out.println("四舍五⼊取整:(2.9)=" + new BigDecimal("2.9").setScale(0, BigDecimal.ROUND_HALF_UP)); System.out.println("凑整:Math.ceil(2)=" + (int)Math.ceil(i));System.out.println("凑整:Math.ceil(2.1)=" + (int)Math.ceil(j));System.out.println("凑整:Math.ceil(2.5)=" + (int)Math.ceil(k));System.out.println("凑整:Math.ceil(2.9)=" + (int)Math.ceil(m));System.out.println("舍掉⼩数取整:Math.floor(-2)=" + (int)Math.floor(-i));System.out.println("舍掉⼩数取整:Math.floor(-2.1)=" + (int)Math.floor(-j));System.out.println("舍掉⼩数取整:Math.floor(-2.5)=" + (int)Math.floor(-k));System.out.println("舍掉⼩数取整:Math.floor(-2.9)=" + (int)Math.floor(-m));System.out.println("四舍五⼊取整:(-2)=" + new BigDecimal("-2").setScale(0, BigDecimal.ROUND_HALF_UP));System.out.println("四舍五⼊取整:(-2.1)=" + new BigDecimal("-2.1").setScale(0, BigDecimal.ROUND_HALF_UP)); System.out.println("四舍五⼊取整:(-2.5)=" + new BigDecimal("-2.5").setScale(0, BigDecimal.ROUND_HALF_UP)); System.out.println("四舍五⼊取整:(-2.9)=" + new BigDecimal("-2.9").setScale(0, BigDecimal.ROUND_HALF_UP)); System.out.println("凑整:Math.ceil(-2)=" + (int)Math.ceil(-i));System.out.println("凑整:Math.ceil(-2.1)=" + (int)Math.ceil(-j));System.out.println("凑整:Math.ceil(-2.5)=" + (int)Math.ceil(-k));System.out.println("凑整:Math.ceil(-2.9)=" + (int)Math.ceil(-m));}}//_____________________________舍掉⼩?取整:Math.floor(2)=2舍掉⼩?取整:Math.floor(2.1)=2舍掉⼩?取整:Math.floor(2.5)=2舍掉⼩?取整:Math.floor(2.9)=2四舍五⼊取整:(2)=2四舍五⼊取整:(2.1)=2四舍五⼊取整:(2.5)=3四舍五⼊取整:(2.9)=3整:Math.ceil(2)=2整:Math.ceil(2.1)=3整:Math.ceil(2.5)=3整:Math.ceil(2.9)=3舍掉⼩?取整:Math.floor(-2)=-2舍掉⼩?取整:Math.floor(-2.1)=-3舍掉⼩?取整:Math.floor(-2.5)=-3舍掉⼩?取整:Math.floor(-2.9)=-3四舍五⼊取整:(-2)=-2四舍五⼊取整:(-2.1)=-2四舍五⼊取整:(-2.5)=-3四舍五⼊取整:(-2.9)=-3整:Math.ceil(-2)=-2整:Math.ceil(-2.1)=-2整:Math.ceil(-2.5)=-2整:Math.ceil(-2.9)=-2===================================================BigDecimal b = new BigDecimal(9.655 );//double f1 = b.setScale(2, BigDecimal.ROUND_HALF_UP).doubleValue();double f1 = b.setScale(2, BigDecimal.ROUND_HALF_UP).doubleValue();System.out.println("f1=" + f1);//f1=9.65BigDecimal mData = new BigDecimal("9.655").setScale(2, BigDecimal.ROUND_HALF_UP);System.out.println("mData=" + mData);//mData=9.66public BigDecimal(double val)将 double 转换为 BigDecimal,后者是 double 的⼆进制浮点值准确的⼗进制表⽰形式。
详解java的四舍五入与保留位
数的操作四舍五入是咱们小学的数学问题,这个问题对于咱们程序猿来讲就类似于1到10的加减乘除那么简单了。
在讲解之间咱们先看如下一个经典的案例:public static void main(String args[]){"的四舍五入的值: "+);"的四舍五入的值: "+);}控制台输出:这是四舍五入的经典案例,也是咱们参加校招时候常常会碰到的(貌似我参加笔试的时候碰到过好多次)。
从这儿结果中咱们发现这两个绝对值相同的数字,为何近似值会不同呢?其实这与采用的四舍五入规则来决定。
四舍五入其实在金融方面运用的超级多,尤其是银行的利息。
咱们都知道银行的盈利渠道主如果利息差,它从储户手里搜集资金,然后放贷出去,期间产生的利息差就是银行所取得的利润。
若是咱们采用平常四舍五入的规则话,这里采用每10笔存款利息计算作为模型,如下:四舍:、、、、。
这些舍的都是银行赚的钱。
五入:、、、、。
这些入的都是银行亏的钱,别离为:、、.003、、。
所以对于银行来讲它的盈利应该是+ + + + - - - - - = 。
从结果中可以看出每10笔的利息银行可能就会损失元,万万别小看这个数字,这对于银行来讲就是一笔超级大的损失。
面对这个问题就产生了如下的银行家涉入法了。
该算法是由美国银行家提出了,主要用于修正采用上面四舍五入规则而产生的误差。
如下:舍去位的数值小于5时,直接舍去。
舍去位的数值大于5时,进位后舍去。
当舍去位的数值等于5时,若5后面还有其他非0数值,则进位后舍去,若5后面是0时,则按照5前一名数的奇偶性来判断,奇数进位,偶数舍去。
对于上面的规则咱们举例说明= ------六入= -----四舍= -----五后有数进位= -----五后无数,若前位为偶数应舍去= -----五后无数,若前位为奇数应进位下面实例是利用银行家舍入法:public static void main(String args[]){BigDecimal d=new BigDecimal(100000); etScale(2,;oubleValue();0");0 表示两位小数#.0000四位小数以此类推…方式三:public static void main(String args[]){double f=;String result=("%.2f", f);f %. 表示小数点前任意位数 2 表示两位小数格式后的结果为f 表示浮点型。
BigDecimal高精度计算熟悉扩展,java除法保留小数问题
BigDecimal⾼精度计算熟悉扩展,java除法保留⼩数问题java保留两位⼩数问题:⽅式⼀:四舍五⼊double f = 111231.5585;BigDecimal b = new BigDecimal(f);double f1 = b.setScale(2, BigDecimal.ROUND_HALF_UP).doubleValue();保留两位⼩数---------------------------------------------------------------⽅式⼆:java.text.DecimalFormat df =new java.text.DecimalFormat("#.00");df.format(你要格式化的数字);例:new java.text.DecimalFormat("#.00").format(3.1415926)#.00 表⽰两位⼩数 #.0000四位⼩数以此类推...⽅式三:double d = 3.1415926;String result = String .format("%.2f");%.2f %. 表⽰⼩数点前任意位数 2 表⽰两位⼩数格式后的结果为f 表⽰浮点型⽅式四:NumberFormat ddf1=NumberFormat.getNumberInstance() ;void setMaximumFractionDigits(int digits)digits 显⽰的数字位数为格式化对象设定⼩数点后的显⽰的最多位,显⽰的最后位是舍⼊的import java.text.* ;import java.math.* ;class TT{public static void main(String args[]){ double x=23.5455;NumberFormat ddf1=NumberFormat.getNumberInstance() ;ddf1.setMaximumFractionDigits(2);String s= ddf1.format(x) ;System.out.print(s);}}---------------------------------------------------------------------------------------------------------有⼀篇:(1)、浮点数精确计算胜利油⽥三流合⼀项⽬中⼀直存在⼀个问题,就是每次报表统计的物资⾦额和实际的⾦额要差那么⼏分钱,和实际⾦额不⼀致,让客户觉得总是不那么舒服,原因是因为我们使⽤java的浮点类型double来定义物资⾦额,并且在报表统计中我们经常要进⾏⼀些运算,但Java中浮点数(double、float)的计算是⾮精确计算,请看下⾯⼀个例⼦:System.out.println(0.05 + 0.01);System.out.println(1.0 - 0.42);System.out.println(4.015 * 100);System.out.println(123.3 / 100);你的期望输出是什么?可实际的输出确实这样的:0.0600000000000000050.5800000000000001401.499999999999941.2329999999999999这个问题就⾮常严重了,如果你有123.3元要购买商品,⽽计算机却认为你只有123.29999999999999元,钱不够,计算机拒绝交易。
java四舍五入算法
Java四舍五入算法简介四舍五入是一种常用的数值处理方式,它可以在确定位数之后,将小数点后的数字进行近似取舍,取到最接近的整数或指定小数位数的小数。
在Java中,提供了多种四舍五入的方法和算法。
本文将介绍Java中四舍五入的算法以及相关的应用场景和注意事项。
四舍五入算法在Java中,可以使用以下两种方式进行四舍五入:1.使用Math类的round方法:Math.round(double d)2.使用BigDecimal类的setScale方法:BigDecimal.setScale(int newScale,RoundingMode roundingMode)Math类的round方法Math.round方法可以对一个double类型的数值进行四舍五入,并返回一个long类型的结果。
该方法的原理是将小数点后的数值加上0.5,然后进行向下取整,即截取掉小数点后的部分。
以下是使用Math.round方法进行四舍五入的示例代码:double number = 3.14;long roundedNumber = Math.round(number);System.out.println("Rounded number: " + roundedNumber);输出结果为:Rounded number: 3BigDecimal类的setScale方法BigDecimal类提供了更精确的数值计算和四舍五入操作。
setScale方法可以对一个BigDecimal对象设置精度,并指定四舍五入的模式。
常用的四舍五入模式有:•RoundingMode.UP:向上舍入•RoundingMode.DOWN:向下舍入•RoundingMode.HALF_UP:向上舍入,如果小数点后一位大于等于5,则进位•RoundingMode.HALF_DOWN:向下舍入,如果小数点后一位大于5,则进位以下是使用BigDecimal.setScale方法进行四舍五入的示例代码:BigDecimal number = new BigDecimal("3.14");BigDecimal roundedNumber = number.setScale(0, RoundingMode.HALF_UP);System.out.println("Rounded number: " + roundedNumber);输出结果为:Rounded number: 3四舍五入的应用场景四舍五入算法在实际应用中非常常见,特别是涉及到金额、百分比等需要精确控制小数位数的场景。
Java修约精度(四舍五入、四舍六入,0.5修约、10修约)
Java修约精度(四舍五⼊、四舍六⼊,0.5修约、10修约)⼀、Java数值、精度、修约规则//规则://四舍六⼊五考虑,//五后⾮零就进⼀,//五后皆零看奇偶,//五前为偶应舍去,//五前为奇要进⼀。
/*** 数值、精度、修约规则** @param value:数值* @param places:精度(1、0.5、10、0.1、0.01...)* @param even:修约(四舍五⼊、四舍六⼊)* @return {BigDecimal}*/public static String evenRound(Object value, Object places,Object even) {if (places == null || even == null) {String value2 = toStr(value);return value2;}String value2 = toStr(value);String places2 = toStr(places);String even2 = toStr(even);//数值和精度不可以为空if (StringUtil.isEmpty(value2) || StringUtil.isEmpty(places2) || StringUtil.isEmpty(even2)) return value2;try {BigDecimal num = new BigDecimal(value2);Integer decimalPlaces = 0;//默认是四舍六⼊Integer evenRound = (even2.indexOf("五")>-1||even2.indexOf("5")>-1||even2.indexOf("伍")>-1)?5:6;if (places2.equals("0.5")){//TODO 精度为 0.5 时//(0.75 * 2).修约 / 2BigDecimal rule = new BigDecimal("2");//系数//保留0位⼩数decimalPlaces = 0;if (evenRound==5){//四舍五⼊value2 = ((num.multiply(rule)).setScale(decimalPlaces, BigDecimal.ROUND_HALF_UP).divide(rule,4,BigDecimal.ROUND_HALF_UP)).toString();} else {//四舍六⼊value2 = ((num.multiply(rule)).setScale(decimalPlaces, BigDecimal.ROUND_HALF_EVEN).divide(rule,4,BigDecimal.ROUND_HALF_EVEN)).toString(); }value2 = numDecimal(value2,1);} else if (places2.equals("5")){//TODO 精度为 ”5“ 时,个位只有(0 | 5)//(0.75 * 0.2).修约 / 0.2BigDecimal rule = new BigDecimal("0.2");//系数//保留0位⼩数decimalPlaces = 0;if (evenRound==5){//四舍五⼊value2 = ((num.multiply(rule)).setScale(decimalPlaces, BigDecimal.ROUND_HALF_UP).divide(rule,4,BigDecimal.ROUND_HALF_UP)).toString();} else {//四舍六⼊value2 = ((num.multiply(rule)).setScale(decimalPlaces, BigDecimal.ROUND_HALF_EVEN).divide(rule,4,BigDecimal.ROUND_HALF_EVEN)).toString(); }value2 = numDecimal(value2,0);} else if (places2.equals("10")){。
Java中Math.round()的取整规则
Java中Math.round()的取整规则
做Java的面试题时遇到了以下这题,百度了一下Math.round()的修约规则,有的说是四舍五入,有的说是四舍六入,发现和我学分析化学时用的数字修约规则(四舍六入五成双)很像,所以验证一下;原题:Math.round(11.5) 等于多少?Math.round(-11.5)等于多少?作者给的解题方法如下:
答:Math.round(11.5)的返回值是12,Math.round(-11.5)的返回值是-11。
四舍五入的原理是在参数上加0.5然后进行下取整。
先说结论,题目作者给的解释是对的,后来找了该方法的定义,结果方法的定义就是这个原理,果然看文档才是王道;
round方法:
static long round(double a)
此方法返回的参数最接近的long.
static int round(float a)
此方法返回的参数最接近的整数.
注:四舍六入五成双:
当有效位数确定后,其后面多余的数字应该舍去,只保留有效数字最末一位,这种修约(舍入)规则是“四舍六入五成双”,也即“4舍
6入5凑偶”这里“四”是指≤4 时舍去,”六”是指≥6时进上,”五”指的是根据5后面的数字来定,当5后有数时,舍5入1;当5后无有效数字时,需要分两种情况来讲:①5前为奇数,舍5入1;
②5前为偶数,舍5不进。
(0是偶数)。
- 1、下载文档前请自行甄别文档内容的完整性,平台不提供额外的编辑、内容补充、找答案等附加服务。
- 2、"仅部分预览"的文档,不可在线预览部分如存在完整性等问题,可反馈申请退款(可完整预览的文档不适用该条件!)。
- 3、如文档侵犯您的权益,请联系客服反馈,我们会尽快为您处理(人工客服工作时间:9:00-18:30)。
数的操作
四舍五入是我们小学的数学问题,这个问题对于我们程序猿来说就类似于1到10的加减乘除那么简单了。
在讲解之间我们先看如下一个经典的案例:
public static void main(String args[]){
System.out.println("12.5的四舍五入的值: "+Math.round(12.5));
System.out.println("-12.5的四舍五入的值: "+Math.round(-12.5));
}
控制台输出:
这是四舍五入的经典案例,也是我们参加校招时候经常会遇到的(貌似我参加笔试的时候遇到过好多次)。
从这儿结果中我们发现这两个绝对值相同的数字,为何近似值会不同呢?其实这与Math.round 采用的四舍五入规则来决定。
四舍五入其实在金融方面运用的非常多,尤其是银行的利息。
我们都知道银行的盈利渠道主要是利息差,它从储户手里收集资金,然后放贷出去,期间产生的利息差就是银行所获得的利润。
如果我们采用平常四舍五入的规则话,这里采用每10笔存款利息计算作为模型,如下:四舍:0.000、0.001、0.002、0.003、0.004。
这些舍的都是银行赚的钱。
五入:0.005、0.006、0.007、0.008、0.009。
这些入的都是银行亏的钱,分别为:0.005、0.004、.003、0.002、0.001。
所以对于银行来说它的盈利应该是0.000 + 0.001 + 0.002 + 0.003 + 0.004 - 0.005 - 0.004 - 0.003 - 0.002 - 0.001 = -0.005。
从结果中可以看出每10笔的利息银行可能就会损失0.005元,千万别小看这个数字,这对于银行来说就是一笔非常大的损失。
面对这个问题就产生了如下的银行家涉入法了。
该算法是由美国银行家提出了,主要用于修正采用上面四舍五入规则而产生的误差。
如下:舍去位的数值小于5时,直接舍去。
舍去位的数值大于5时,进位后舍去。
当舍去位的数值等于5时,若5后面还有其他非0数值,则进位后舍去,若5后面是0时,则根据5前一位数的奇偶性来判断,奇数进位,偶数舍去。
对于上面的规则我们举例说明
11.556 = 11.56 ------六入
11.554 = 11.55 -----四舍
11.5551 = 11.56 -----五后有数进位
11.545 = 11.54 -----五后无数,若前位为偶数应舍去
11.555 = 11.56 -----五后无数,若前位为奇数应进位
下面实例是使用银行家舍入法:
public static void main(String args[]){
BigDecimal d=new BigDecimal(100000); //存款金额
BigDecimal r=new BigDecimal(0.001875*3); //利率
BigDecimal i=d.multiply(r).setScale(2,RoundingMode.HALF_EVEN);
//使用银行家算法,保留位为2位,multiply(r)为乘法运算
System.out.println("季利息是:"+i);
}
控制台输出
在上面简单地介绍了银行家舍入法,目前java支持7中舍入法:
1、 ROUND_UP:远离零方向舍入。
向绝对值最大的方向舍入,只要舍弃位非0即进位。
2、 ROUND_DOWN:趋向零方向舍入。
向绝对值最小的方向输入,所有的位都要舍弃,不存在进位情况。
3、 ROUND_CEILING:向正无穷方向舍入。
向正最大方向靠拢。
若是正数,舍入行为类似于ROUND_UP,若为负数,舍入行为类似于ROUND_DOWN。
Math.round()方法就是使用的此模式。
4、 ROUND_FLOOR:向负无穷方向舍入。
向负无穷方向靠拢。
若是正数,舍入行为类似于ROUND_DOWN;若为负数,舍入行为类似于ROUND_UP。
5、 HALF_UP:最近数字舍入(5进)。
这是我们最经典的四舍五入。
6、 HALF_DOWN:最近数字舍入(5舍)。
在这里5是要舍弃的。
7、 HAIL_EVEN:银行家舍入法。
提到四舍五入那么保留位就必不可少了,在java运算中我们可以使用多种方式来实现保留位。
保留位
方法一:四舍五入
public static void main(String args[]){
double f=111231.5585;
BigDecimal d=new BigDecimal(f);
double e=d.setScale(2, RoundingMode.HALF_UP).doubleValue();
//RoundingMode.HALF_UP 典型的四舍五入
System.out.println(" f 保留两位的四舍五入值:"+e);
}
控制台输出:
在这里使用BigDecimal ,并且采用setScale方法来设置精确度,同时使用RoundingMode.HALF_UP 表示使用最近数字舍入法则来近似计算。
在这里我们可以看出BigDecimal和四舍五入是绝妙的搭配。
方式二:
public static void main(String args[]){
java.text.DecimalFormat df=new java.text.DecimalFormat("#.00");
//类似于日期里的SimpleDateFormat
String result=df.format(111231.5585);
//df.format(你要格式化的数字);
System.out.println("四舍五入后的结果:"+result);
}
控制台输出:
例:new java.text.DecimalFormat(”#.00″).format(3.1415926)
#.00 表示两位小数 #.0000四位小数以此类推…
方式三:
public static void main(String args[]){
double f=111231.5585;
String result=String.format("%.2f", f);
//%.2f %. 表示小数点前任意位数 2 表示两位小数格式后的结果为f 表示浮点型。
System.out.println("四舍五入后的结果: "+result);
}
控制台输出:
方式四:
此外如果使用struts标签做输出的话,有个format属性,设置为format="0.00"就是保留两位小数
<bean:write name="entity" property="dkhAFSumPl" format="0.00" />
或者
<fmt:formatNumber type="number" value="${10000.22/100}" maxFractionDigits="0"/>
maxFractionDigits表示保留的位数。