我确实在下面的代码中评论问题所在,当调用pow函数时,exp参数变得疯狂。代码的目标是接收用户输入并解决该表达式x /(1 + t)^ n。
#define _CRT_SECURE_NO_WARNINGS
#include <stdio.h>
float val();
float pow();
float val(float x, int n, float t) {
float res = 0;
for (int i = 0; i < n; i++) {
printf("exp = %d\n", i+1); // real value exp start equals 1
res += x / pow(1 + t, i+1);
}
return res;
}
float pow(float base, int exp) {
int i = 0;
float res = 1;
printf("exp = %d", exp); // here starts the problem
if (exp == 1) {
return base;
}
while (i < exp) {
res *= base;
i++;
printf("i = %d\n", i);
printf("exp = %d\n", exp);
getchar();
}
return res;
}
main() {
int n;
float x, t, res;
printf("type x,n,t\n");
scanf("%f %d %f", &x, &n, &t);
res = val(x, n, t);
printf("VAL = %f\n", res);
}
输出:
type x,n,t
6
2
2
exp = 1
exp = 1074266112i = 1
exp = 1074266112
i = 2
exp = 1074266112
发生了什么事? 谢谢你的关注:))
答案 0 :(得分:4)
不要使用旧式弃用的非原型前向声明:
float val(); /* This syntax should never be used */
float pow();
声明函数时,声明其完整原型:
float val(float x, int n, float t);
float pow(float base, int exp);
另外,请考虑使用double
而不是float
。
从最初的结果可能会猜到,你的程序表现出未定义的行为;在这种情况下,使用与其参数类型不兼容的参数类型调用pow
。旧式的已弃用声明样式
float pow();
没有指定pow
的参数类型是什么,甚至没有指定它的期望值。实际上,它告诉编译器“相信我,我将提供正确类型的参数。”
但是因此不可能遵守该承诺,因为pow
期望float
作为其第一个参数,并且编译器对提供给没有原型声明的函数的所有参数执行默认参数提升。其中一个默认促销活动会将float
转换为double
,因此无法提供float
参数。如果你使用double
而不是float
s,你就不会遇到这个特殊的问题而且你可能会继续使用一种近30年来一直被劝阻的语法。
顺便说一下,val
中没有出现此问题,因为val
的定义在您使用之前就已发生。当然,该定义确实指定了参数类型,并且填写了无原型前向声明中省略的信息。
但底线是上面提供的简单建议:不要使用旧式函数声明。应使用完整原型声明每个函数,并指定其所有参数的类型。 (如果需要声明不带参数的函数,请使用特殊参数列表(void)
而不是空参数列表。)
答案 1 :(得分:0)
pow:
float pow(float base, int exp)
{
float res = 1;
if (exp > 0)
{
while(exp --)
{
res *= base;
}
}
else
{
while(exp ++)
{
res /= base;
}
}
return res;
}
main()
{
int i;
for (i = -5; i <= 5; i++)
{
printf("5 ^^ %d = %f\n", i, pow(5.0f,i));
}
}
并完成
#include <stdio.h>
float power(float base, int exp)
{
float res = 1;
if (exp > 0)
{
while(exp --)
{
res *= base;
}
}
else
{
while(exp ++)
{
res /= base;
}
}
return res;
}
float eq(float x, float t, int n)
{
return x / power(1 + t, n);
}
int main()
{
float x,t;
int i,n;
for (i = -5; i <= 5; i++)
{
printf("5 ^^ %d = %f\n", i, power(5.0f,i));
}
scanf("%f %f %d\n", &x, &t, &n);
printf("x = %f, t = %f, n = %d\n", x, t, n);
printf("1/(1+t)^^n = %f", eq(x, t, n));
}