这个问题陷阱在于没有规定n位数的位数,也就是说这个n可能是10000,这样的话,int和long long都无法存储,所以采用string字符串来存储这个数字, 第二个陷阱是在打印字符串的时候不能从头到尾全打印,要从第一个非零的数开始打印。
类声明如下:
#pragma once
#include<iostream>
using namespace std;
class printNumber
{
public:
printNumber();
~printNumber();
void print1ToMaxOfDigits(int n); // 主体函数
bool Increment(char * digits); // 用于递增字符串代表的数字
void PrintAllOfNumber(char * digits); // 用于打印一个字符串
};
实现如下:
#include "stdafx.h"
#include "printNumber.h"
printNumber::printNumber()
{
}
printNumber::~printNumber()
{
}
void printNumber::print1ToMaxOfDigits(int n)
{
char * digitsStr = new char[n + 1];
memset(digitsStr, '0', n);
digitsStr[n] = '\0';
while (!Increment(digitsStr))
{
PrintAllOfNumber(digitsStr);
}
delete[] digitsStr;
}
bool printNumber::Increment(char * digitsStr)
{
bool isOverFlow = false;
int nTakeOver = 0;
int nLength = strlen(digitsStr);
for (int i = nLength-1; i >= 0; i--)
{
int tmpBit = 0;
// 首先判断是不是个位, 如果是个位,先单纯加1
if (i == nLength-1)
{
tmpBit = digitsStr[i] - '0' + 1;
}
// 如果不是各位需要看前面是否有进位
else
{
tmpBit = digitsStr[i] - '0' + nTakeOver;
}
// 看加了之后是不是需要向前进位
if (tmpBit >= 10) // 需要进位
{
// 如果进位的是最高位,则溢出
if (i == 0)
{
isOverFlow = true;
}
// 如果进位的不是最高位,则向前进位,且该位取个位数的值
else
{
digitsStr[i] = '0' + tmpBit - 10;
nTakeOver = 1;
break; // 这个地方的break与冒泡算法的改进中的标志位作用类似,避免后面的比必要的循环。
}
}
else // 不需要向前进位的情况,单纯置值即可
{
digitsStr[i] = '0' + tmpBit;
nTakeOver = 0; // 进位值置0
}
}
return isOverFlow;
}
void printNumber::PrintAllOfNumber(char * digitsStr)
{
bool isBeginingZero = true;
while (*digitsStr != '\0')
{
if (*digitsStr != '0')
{
isBeginingZero = false;
}
if (!isBeginingZero)
{
cout << *digitsStr;
}
++digitsStr;
}
cout << endl;
}