[重返NOIP] 高精度——NOIP1998 普及组 阶乘之和
题目描述 用高精度计算出 S = 1! + 2! + 3! + … + n! ( n <= 50 )。 其中 ! 表示阶乘,定义为 n!=n (n-1) (n-2) … 1 。例如, 5! = 5 4 3 2 1=120 。 输入格式 一个正整数 n 。 输出格式 一个正整数 S ,表示计算结果。 样例 #1 样例输入 #1 3 样例输出 #1 9 提示 【数据范围】 对于 100 % 的数据, 1 <= n <= 50 。 思路 看了一下大部分题解,其实也没有别的考察点,主要就是高精加套高精乘,方法也有很多,下面主要介绍两种该思路的实现方法 方法一 这种方法主要使用结构体去封装大整数,让大整数能像普通整型一样直接相加相乘,下面是封装的结构体 #define MAXN 50000 struct bigint{ int len,a[MAXN];//len记录位数,a记录每个数位 bigint(int x=0){//通过初始化使得这个大整数能够表示整型x,默认为0 memset(a,0,sizeof(a)); for(len=1;x;len++){ a[len]=x%10,x/=10; } len--; } int &operator[](int i){ return a[i]; //重载[],可以直接用x[i]代表x.a[i] } void flatten(int L){//一口气处理1到L范围内的进位并重置长度。需要保证L不小于有效长度 //简单说就是将数组每个位置经过进位后都变成一位数 len=L; for(int i=1;i<=len;i++){ a[i+1]+=a[i]/10; a[i]%=10; } for(;!a[len];){//重置长度为有效长度 len--; } } void print(){ for(int i=max(len,1);i>=1;i--){ printf("%d",a[i]); } } bigint operator+(bigint a,bigint b){//表示两个bigint类相加,返回一个bigint类 bigint c; int len=max(a.len,b.len); for(int i=1;i<=len;i++){ c[i]+=a[i]+b[i]; } c.flatten(len+1);//答案不可能超过len+1位,所以用len+1做进位处理 return c; } bigint operator*(bigint a,bigint b){ bigint c; int len=a.len; for(int i=1;i<=len;i++){ c[i]=a[i]*b; } c.flatten(len+1);//int类型最长10位,所以可以这样做一遍进位处理 } }; 封装完后,就需要主函数对接接口直接使用了 ...