《剑指offer》Java学习录:面试题 12:打印1到最大的n位数

面试题 12:打印1到最大的n位数

题目

输入数字n,按顺序打印出从1到最大的n位十进制数。比如输入3,则打印出1、2、3一直到最大的3位数即999。

分析

如果不作分析,可能直接就会采用:算出n位数的最大值,然后循环输出就完事儿了。但这个题显然不是这么简单,题目中没有给n做任何限定,如果n的值很大,那么不管是double还是long类型都无法承担存储大数的责任。

在java中处理大数大概有三种方案:

  • 使用String模拟大数,需要自己实现加法操作。
  • 使用数组模拟大数,也需要自己实现加法操作。
  • 使用BigDecimal。

本例中,使用int数组来模拟大数操作。

解:java

public static void main(String args[]) {
    printToMaxNDigits(2);
}
public static void printToMaxNDigits(int n) {
    if (n <= 0) { // 输入边界检查,防止-1、0之类的非法输入
        return;
    }
    int[] number = new int[n];
    while(increment(number)) { // increment的作用是 + 1,+ 1成功返回true,去打印否则结束循环
        printNumber(number);
    }
}
private static boolean increment(int[] number) {
    if (number == null || number.length == 0) { // 可能出现的边界检查
        throw new IllegalArgumentException("number is empty");
    }

    for (int i = number.length - 1; i >= 0; i--) { // 模拟加法操作,从低位到高位遍历
        if (number[i] < 9) { // 0~8 原地 +1
            number[i] += 1;
            return true;
        } else { // 9置零,下次循环是将高位进1
            number[i] = 0;
        }
    }
    return false;
}
// 直接打印数组将出现[0, 0, 1]这种情况,高位为0不符合阅读习惯,需要自己实现打印函数
private static void printNumber(int[] number) {
    if (number == null || number.length == 0) { // 可能出现的边界检查
        throw new IllegalArgumentException("number is empty");
    }
    
    boolean hasPrint = false;
    for (int i = 0; i < number.length; i++) { // 从高位向低位遍历
        if (number[i] != 0 || hasPrint) { // 当遇到第一个不为零时开始打印
            hasPrint = true;
            System.out.print(number[i]);
        }
    }
    System.out.println();
}
發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章