一道來自洛谷的求階乘之和的題
由于題目中給出的資料范圍較大,即使用 long long 也會造成資料溢位,所以要用到高精度的運算.
學習了高精度運算之后就知道,可以用陣列來儲存范圍大的整數,于是,這道題我就是將資料從1開始依次相乘,每乘一次就將結果保存盡陣列當中,然后與前一次乘積結果相加以達到高精度求和的目的.
以下是我寫的代碼.
#include <iostream>
#include <cstring>
#include <algorithm>
using namespace std;
const int MAXN = 100;
int a[MAXN], b[MAXN], c[MAXN];//a 儲存本次乘積結果, b 儲存上次乘積結果,c 儲存 a和b之和;
int len = 1; // 資料長度;
void sum()
{
for (int i = 0; i <= len; i++)
{
c[i] += a[i] + b[i]; //對每一位進行求和;
c[i + 1] += c[i] / 10;// 模擬加法進位;
c[i] %= 10;
}
if (c[len])//最后進位可能會導致位數增加;
len++;
}
void mp(int y)
{
memset(b, 0, sizeof(b));//初始化陣列 b;
for (int i = 0; i < len; i++)
{
a[i] *= y; // 讓 a 陣列中每一位數都乘上 y,完成高精度數和整型數的乘積;
}
for (int i = 0; i < len; i++) // 模擬乘積后的進位.
{
a[i+1] += a[i] / 10;
a[i] %= 10;
}
int x = a[len];
while (x) // 重置長度 len,使陣列每一位都是個位數;
{
a[len] = x % 10;
x /= 10;
len++;
}
sum();
for (int i = 0; i <= len; i++)
{
b[i] = a[i];
}
}
int main ()
{
int n;
a[0] = 1;
cin >> n;
for (int i = 1; i <= n; i++)
{
mp(i);
}
for (;!c[len];)//重置長度,保留有效長度;
len--;
for (int i = len; i >= 0; i--)
cout << c[i];
return 0;
}
轉載請註明出處,本文鏈接:https://www.uj5u.com/qita/261380.html
標籤:其他
