问题描述
你好,我写了一个循环来得到给定值 n 除以 n 的阶乘总和,指数递增。为了更好地描述它,它看起来像这样:
但由于某种原因,每当我输入一个数字时,我的循环总是返回值 1。 这是我的循环:
int nVal,i,j,k,nProduct = 1,nSum = 0,nFactorial = 1;
float fResult;
for (i = 1; i <= nVal; i++)
{
for (j = 1; j <= nVal; j++)
{
nFactorial *= j;
nSum += nFactorial;
}
for (k = 1; k <= nVal; k++)
{
nProduct *= k;
}
fResult += (nSum * 1.0) / (nProduct * 1.0);
}
我可以尝试任何修复吗?
解决方法
OP 的代码在分子和分母计算中不正确。此外,整数数学很容易溢出。
为了更好地处理大 n
,请使用浮点数学根据先前项形成每个项。
double sum_fact_expo(int n) {
double sum = 0.0;
double ratio = 1.0;
for (int i = 1; i <= n; i++) {
ratio *= 1.0*i/n;
sum += ratio;
}
return sum;
}
,
n
会有多大?这可以指定 nProduct
和 nFactorial
的类型(例如 int
或 long long
或 __int128
或 double
)。
嵌套/内部循环是错误的。您只需要/需要 for
的 i
循环。
如果您等待计算比率,您将 [可能/很可能] 上溢/下溢。所以,在每次迭代时都这样做。
你的阶乘计算线没问题。但是,nProduct
计算不正确。乘数必须是 n
[而不是 j
]。
您没有初始化 fResult
,因此它以随机值开始(即未定义的行为)。如果您使用 -Wall
[和 -O2
] 进行编译以启用警告,则会被标记。
记住:
k! = (k - 1)! * k
而且,那个:
n**k = n**(k - 1) * n
因此,我们可以在一个循环中迭代地构建 nFactorial
子项和 nProduct
子项。
我认为您的代码应该是这样的:
// pick _one_ of these:
#if 0
typedef int acc_t;
#endif
#if 0
typedef long long acc_t;
#endif
#if 0
typedef __int128 acc_t;
#endif
#if 1
typedef double acc_t;
#endif
double
calc1(int nVal)
{
int i;
acc_t nProduct = 1;
acc_t nFactorial = 1;
double ratio;
double fResult = 0;
for (i = 1; i <= nVal; ++i) {
nFactorial *= i;
nProduct *= nVal;
ratio = (double) nFactorial / (double) nProduct;
fResult += ratio;
}
return fResult;
}
,
#include <stdio.h>
int main(void) {
int nVal,i,j,k,nProduct = 1,nFactorial = 1;
float fResult = 0;
scanf("%d",&nVal);
for (i = 1; i <= nVal; i++)
{
for (j = 1; j <= i; j++)
{
//calculate 1! 2! 3! ... n!
//actually calculate i!
nFactorial *= j;
}
for (k = 1; k <= i; k++)
{
//calculate n^1 n^2 n^3 ... n^n
//actually calculate n^i
nProduct *= nVal;
}
fResult += (nFactorial * 1.0) / (nProduct * 1.0);
nProduct = 1;
nFactorial = 1;
}
printf("%f\n",fResult);
return 0;
}