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

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



解析:

easy知道不能用 int 等数字类型表示(大数问题)

在字符串上模拟数字加法

关键点:

1. 怎样用字符串表示n位数?

2. 怎样实现字符串数的自增操作?

3. 怎样打印一个字符串数?

- 申请长度是n+1的字符数组number。 number[0] 是最高位, number[n-1]最低位, number[n] = ‘\0’

- 首先把字符串中的每个数字都初始化为’0’ (注意是字符’0’,不是0)。然后每一次为字符串表示的数字加 1.

- 自增操作时。通过最高位是否会产生进位来推断是否到达最大数。

- 打印字符串数时,应该省略掉高位的无效0

#include <iostream>
#include <stdio.h>
using namespace std;
bool Increment(char* number, int n);
void PrintNum(char* number, int n);
void Print1ToMaxOfNDigits(int n) {
    if (n <= 0) // 仅仅要有输入就要考虑输入合法性问题
        return;
    char* number = new char[n + 1]; // 最后一位放 ‘\0‘
    memset(number, ‘0‘, n); // 注意是 ‘0‘ 不是 0
    number[n] = ‘\0‘;
    while (Increment(number, n) == true) {
        PrintNum(number, n);
    }
    delete []number;
}
bool Increment(char* number, int n)
{
    int sum = 0, carry = 0;
    for (int i = n - 1; i >= 0; i--) {
        sum = (number[i] - ‘0‘) + carry;
        if (i == n - 1) // 在末位 + 1
            sum++;
        if (sum >= 10) {
            if (i == 0) // 最高位产生进位,已到达最大数
                return false;
            sum -= 10;
            carry = 1;
            number[i] = ‘0‘ + sum;
        } else {
            number[i] = ‘0‘ + sum; // 已无进位,自增结束
            break;
        }
    }
    return true;
}
void PrintNum(char* number, int n)
{
    int i = 0;
    while (number[i] == ‘0‘) // 跳过前面 ‘0‘
        i++;
    for (; i < n; i++)
        printf("%c", number[i]);
    cout << "  ";
}

int main()
{
    Print1ToMaxOfNDigits(-1);
    Print1ToMaxOfNDigits(0);
    Print1ToMaxOfNDigits(3);
    // Print1ToMaxOfNDigits(10);
}

全排列法递归打印

我们把每位数字都从 0~9 排列一遍就能得到全部的十进制数,仅仅是打印时省略掉高位无效 0

通过递归实现。从最高位開始。每一位都可能是0~9中的一个数。针对每一种可能设置下一位。递归结束条件是当我们设置了数字的最后一位。

void Print1ToMaxOfNDigits2(int n) {
    if (n <= 0)
        return;
    char* number = new char[n + 1];
    memset(number, ‘0‘, n);
    number[n] = ‘\0‘;
    Print1ToMaxOfNDigits2Recurisively(number, n, 0);
}
void Print1ToMaxOfNDigits2Recurisively(char* number, int len, int index) {
    if (index == len) {
        PrintNum(number, len); // 使用上文中的打印函数
        return;
    }
    for (int i = 0; i < 10; i++) {
        number[index] = ‘0‘ + i;
        Print1ToMaxOfNDigits2Recurisively(number, len, index + 1);
    }
}

时间: 2024-10-11 21:02:29

12:打印 1 到最大的 n 位数的相关文章

剑指offer (12) 打印1到最大的n位数

题目描述: 给定一个数字N,打印从1到最大的N位数 此题需要注意以下几点: 1. 涉及到大数问题,因为并没有限定 n的取值范围,所以需要采取 字符数组模拟大数运算 2. 打印数字时 需要忽略前置0 3. 我们始终 以n位数为整体,n位所有十进制数其实是 n位从0到9的全排列,可以采用递归解决 我们从 数组下标0开始 (对应于数字最高位),每一位都有0到9取值,然后设置下一位,递归的结束条件是 设置位到了数组的最末端 1 void PrintNum(char* num) 2 { 3 char* c

数据结构-打印1到最大的n位数

题目:输入数字n,按顺序打印出从1到最大的n位十进制数,比如输入3,则打印出1,2,3一直到最大的3位数即999. 分析:本题最关键的部分是当n值非常大的时候会超出数据类型的范围.偷个懒,没有实现打印1,2,3....999.可以利用分割把string分割成char[].然后单个的char转为int再进行加减法,作为输出. /* 剑指offer面试题12 该问题主要考虑到数据非常大超出数据类型的范围 */ #include <iostream> #include <cstring>

剑指OFFER之打印1到最大的N位数(九度OJ1515)

题目描述: 给定一个数字N,打印从1到最大的N位数. 输入: 每个输入文件仅包含一组测试样例.对于每个测试案例,输入一个数字N(1<=N<=5). 输出: 对应每个测试案例,依次打印从1到最大的N位数. 样例输入: 1 样例输出: 1 2 3 4 5 6 7 8 9 解题思路: 直接通过n快速指定比最大的那个数大1的数,10,100,1000,10000,100000.... 输出,就行了... 代码: #include <stdio.h> int main(void){ int

循环-12. 打印九九口诀表

1 /* 2 * Main.c 3 * C12-循环-12. 打印九九口诀表 4 * Created on: 2014年7月31日 5 * Author: Boomkeeper 6 *******测试通过******** 7 */ 8 9 10 #include <stdio.h> 11 12 int main(void){ 13 14 int N=0;//题目中的N 15 16 scanf("%d",&N); 17 int i, j;//控制行.列 18 for

【C语言】打印1到最大的n位数

//打印1到最大的n位数 //输入数字n,按顺序打印出从1到最大的n位十进制数.比如:输入3,则打印出1.2一直到最大的3位数999 #include <stdio.h> #include <stdlib.h> #include <memory.h> int num[10]; int add(int n) { int isoverflow = 0; int carry = 0; int i; for (i = 9; i >= 10 - n; i--) { num[

打印1到最大的n位数----java实现

题目:输入数字n,按顺序打印出从1到最大的n位十进制数.比如,输入3,则打印出1,2,3,.....,一直到最大的3位数即999. 分析: 1.这是一个典型的大数加法问题,无论是int还是long long类型多无法表示.所以在解决大数问题时,通常是使用字符串或者数组实现其功能(由于个人比较钟爱数组,所以下面代码是使用数组实现的). 2.在大数的加法中,我们需要注意的问题是进位问题. 3.在该题中还需要判断是否为最大的n位整数.这里需要一个小技巧,我们只需判断最高位(第n位)是否要进位,如果需进

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

// 面试题17:打印1到最大的n位数 // 题目:输入数字n,按顺序打印出从1最大的n位十进制数.比如输入3,则 // 打印出1.2.3一直到最大的3位数即999. 解题思路: 首先是一个大陷阱,n有多大?万一大到long long类型都盛不下,你要直接动手写,那写的再正确也是凉凉. 我们考虑到用字符来表示数字,然后把字符打印出来就行了. 书上巴拉巴拉说了一种很复杂的方法,代码量大也比较繁琐,感兴趣的去参考资料看就行了. 这里直接介绍第二种简单的方法,其实打印出从1最大的n位十进制数,实际就是

《剑指offer》第十七题:打印1到最大的n位数

// 面试题17:打印1到最大的n位数 // 题目:输入数字n,按顺序打印出从1最大的n位十进制数.比如输入3,则 // 打印出1.2.3一直到最大的3位数即999. #include <cstdio> #include <memory> void PrintNumber(char* number); bool Increment(char* number); void Print1ToMaxOfNDigitsRecursively(char* number, int length

打印1到最大的n位数——12

输入数字n,按顺序打印出从1到最大的n位十进制数.比如输入3,则打印出1.2.3...一直到最大的3位数即999. 其实一看这个题,就可以想到用一个循环来打印,循环次数就为10的n次方减一,即输入3循环999次依次打印出所对应的值.但是,有一个重要的点就是,如果n的值很大,大到溢出了所能表示的最大整型范围的值,比如用long long数据类型都存放不下了要怎么办呢?这就可以考虑,用字符串的形式来表达大数据,反正只是说让打印出来: 程序设计如下: #include <iostream> #inc