使用printf格式化输出

对于一些的题目,我们可以直接使用printf格式化输出。这里写几个例子。

例题一

问题描述
对于长度为5位的一个01串,每一位都可能是0或1,一共有32种可能。它们的前几个是:
00000
00001
00010
00011
00100

请按从小到大的顺序输出这32种01串。

public static void main(String[] args) {
	for(int i=0;i<32;i++) {
		System.out.printf("%05d\n",Integer.parseInt(Integer.toBinaryString(i)));;
	}
}
  • 这里的%05d意思就是以五位的形式打印,不够的用0填充
  • %.2f 浮点型表示保留两位小数并且进行四舍五入的处理

又联想到了String的格式化保存
String用法

使用DecimalFormat

这个功能强大,适合处理比较复杂的位数保留情况。在这里只简单介绍,更复杂一点的东西用到的时候再去搜索用法。

  • DecimalFormat df = new DecimalFormat(str)

一个解决所有问题,下面的图片说明也十分清楚。👇

java整数转浮点数 java浮点数格式化输出_数字

比如下面的例题,就是求圆面积并且保留7位小数。

public class Main {
	public static void main(String[] args) {
		Scanner sc =new Scanner(System.in);
		int n=sc.nextInt();
		double s = n*n*Math.PI;
		DecimalFormat df = new DecimalFormat("0.0000000");
		System.out.println(df.format(s));
		sc.close();
	} 
}

位数问题看似解决了,那么最后一位怎么取舍呢?

尾数的取舍

DecimalFormat四舍五入的坑

       有时候我们在处理小数保留几位小数时,想到了DecimalFormat这个类的使用,百度搜一把可能用到以下方式。

public static void main(String[] args) {
      String str="3.145";
      System.out.println(round1(str));
}
static String round1(String str){
   double a=Double.parseDouble(str);
    DecimalFormat df=new DecimalFormat("###.00");
   return df.format(a);
}

初看好像没什么问题,四舍五入保留两位小数,最后输出3.15。当然精度要求不高,也无需计较。当涉及到精确统计时,这里的坑来了将上面的字符串改为“5”前面为奇数,如“3.155”,就瓜了,输出3.15。显然这里没满足要求,不是我们学校里的四舍五入。再上一段代码。

static String round2(String str){
     double a=Double.parseDouble(str);
     DecimalFormat df=new DecimalFormat("###.00");
     df.setRoundingMode(RoundingMode.HALF_UP);
     return df.format(a);
}

java整数转浮点数 java浮点数格式化输出_数字_02

这里可以看到这个setRoundingMode()方法可以设定四舍五入的模式,原来四舍五入不光有我们学校里学的那种,还有其他模式。DecimalFormat默认情况下,它使用 RoundingMode.HALF_EVEN,此舍入模式也称为“银行家舍入法”,主要在美国使用。RoundingMode.HALF_UP这个模式才是我们学校里学的标准四舍五入模式。但是经过实际操作,看到程序输出的还是错误答案。以上代码虽然舍了学校型模式仍然不准确,应该将double类型改为BigDecimal类型。

java整数转浮点数 java浮点数格式化输出_java_03


RoundingMode说明

为了能更好理解,我们可以画一个XY轴
RoundingMode.CEILING:取右边最近的整数
RoundingMode.DOWN:去掉小数部分取整,也就是正数取左边,负数取右边,相当于向原点靠近的方向取整
RoundingMode.FLOOR:取左边最近的正数
RoundingMode.HALF_DOWN:五舍六入,负数先取绝对值再五舍六入再负数
RoundingMode.HALF_UP:四舍五入,负数原理同上
RoundingMode.HALF_EVEN:这个比较绕,整数位若是奇数则四舍五入,若是偶数则五舍六入

银行家舍入法说明

银行家舍入法是由IEEE 754标准规定的浮点数取整算法 ,大部分的编程软件都使用的是这种方法。 所谓银行家舍入法,其实质是一种四舍六入五取偶(又称四舍六入五留双)法。其规则是:当舍去位的数值小于5时,直接舍去该位;当舍去位的数值大于等于6时,在舍去该位的同时向前位进一;当舍去位的数值等于5且(5后不为空且非全0)时,在舍去该位的同时向前位进一;当舍去位的数值等于5且(5后为空或全0)时,如果前位数值为奇,则在舍去该位的同时向前位进一,如果前位数值为偶,则直接舍去该位。
简单的说,就是:四舍六入五考虑,五后非空就进一,五后为空看奇偶,五前为偶应舍去,五前为奇要进一


这样就是对了,但是我们不需要因为一个四舍五入把程序写的这么麻烦。

使用相对简单实用的方法

用String的fomat方法直接格式化

因为这里是直接默认四舍五入,所以简单可以直接使用此方法。

java整数转浮点数 java浮点数格式化输出_四舍五入_04


java整数转浮点数 java浮点数格式化输出_java_05


这里%05.2f中的5表示的是一共多少个字符,比如上面就是有03.12一共五个字符,2是保留几位小数,默认四舍五入。

static String round3(String str){
     double d=Double.parseDouble(str);
     return String.format("%.2f",d);
}

另外我也总结了String、buffer、builder的方法欢迎学习。

BigDecimal结合DecimalFormat

BigDecimal比较耗性能,数据处理量大不建议使用。

static String round4(String str){
    BigDecimal bigDecimal=new BigDecimal(str);
    DecimalFormat df=new DecimalFormat("###.00");
    df.setRoundingMode(RoundingMode.HALF_UP);
    return df.format(bigDecimal);
}
BigDecimal单独使用,这个类也自带舍入模式设定方法。
static String round5(String str){
        BigDecimal bigDecimal=new BigDecimal(str);
        return String.valueOf(bigDecimal.setScale(2,RoundingMode.HALF_UP));
}
BigDecimal的取舍模式

java整数转浮点数 java浮点数格式化输出_System_06

自己写方法

当然了,如果只是简单的四舍五入,也可以自己单独想一个取舍的好方法。比如下题。

蓝桥杯2020Java成绩统计 在这里面我就是自己写了一个四舍五入的方法,没用别的。