您的位置:首页 > Web前端

剑指offer---17(打印1到最大n位数)

2018-02-01 20:54 316 查看
更多题目请点链接:《剑指offer》目录索引

问题描述:

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

思路1:

(1)此题可归为大数处理问题:n可能很大,打印最大的n位数就存在溢出现象

(2)解决方法:采用高精度算法;使用一个数组arr来表示所要打印的数,将其以字符串的形式存储,并模拟数字加法

(3)加法进位:分析进位时,发现只有9、99、999、9999…….进行加1时,最高位才会发生进位故当加到这些数字时,需要发生进位

(4)最大的n位数:由上面所分析的进位问题,我们发现这些数字发生进位之后,数字就会比当前数字多一位,故这些数字(9、99、999….)为最大的n位数

(5)打印:由于我们将这些数字保存时,arr[0]为高位,如果不做处理,打印2位数时就会打印出这样一系列数:01 02 03 04………为了避免这样的情况,我们加一标记进行判断,从高位开始遍历,当遇到不是字符’0’的字符,即为要打印的数

代码:

void Print1ToMax(int n)
{
assert(n>0);
//将数字存放到数组当中
char* arr = (char*)malloc(sizeof(char)*(n + 1));
assert(arr);
memset(arr, '0', sizeof(char)*n);
arr
= '\0';

while(IncreamNumber(arr)==0)
{
//加法到最大数,开始打印
PrintNumber(arr);
}
free(arr);
arr = NULL;
}

int IncreamNumber(char* arr)
{
int i = 0, nbit = 0;
int len = strlen(arr);

for (i = len - 1; i >= 0; i--)
{
//将字符转化为数字
int sum = arr[i] - '0' + nbit;

//如果在最低位,进行加法
if (i == len - 1)
sum++;

if (sum >= 10)
{
if (i == 0)
{
//如果在最高位要进位,表示已经打印到最大数,返回1
return 1;
}
else
{
//如果没有在最高位,需要进位,则将进位变量置1
sum -= 10;
nbit = 1;
arr[i] ='0'+sum;
}
}
else
{
//如果不需要进位,直接存放到数组中
arr[i] = sum + '0';
break;
}
}
return 0;
}

void PrintNumber(char* arr)
{
int i = 0, flag = 1;
int len = strlen(arr);

for (i = 0; i < len; i++)
{
if (flag == 1 && arr[i] != '0')
{
//当遇到需要的数字时,flag置0
flag = 0;
}

if (flag==0)
{
printf("%c", arr[i]);
}
}
printf("\t");

}


思路2:

方法:采用递归排列方式来打印我们所需要的数;

思想:数学中只有0~9这10个数字,不管是1位数还是2位数还是3位数等等,都是这10个数字的排列而来;因此我们只需在相应的位数上排列这10个数字,在打印这些数字

相应位排列:先排列最高位,在排列次高位,直到最低位即可

代码:

void Print1ToMaxR(int n)
{
assert(n>0);
//将数字存放到数组当中
char* arr = (char*)malloc(sizeof(char)*(n + 1));
assert(arr);
memset(arr, '0', sizeof(char)*n);
arr
= '\0';
int i = 0;
for (i = 0; i < 10; i++)
{
//最高位排列
arr[0] = i + '0';
Print1ToMaxNumberR(arr, n, 0);
}

free(arr);
arr = NULL;
}

void Print1ToMaxNumberR(char* arr, int  len, int index)
{
if (index == len - 1)
{
PrintNumber(arr);
return;
}

for (int i = 0; i < 10; ++i)
{
//在排列次高位到最低位的值
arr[index + 1] = i + '0';
Print1ToMaxNumberR(arr, len, index + 1);
}
}
内容来自用户分享和网络整理,不保证内容的准确性,如有侵权内容,可联系管理员处理 点击这里给我发消息
标签: