#include <stdio.h>
int fibo(int);
int main() {
int n, p[100];
scanf("%d", &n);
int i = 0;
do {
p[i] = fibo(i);
i++;
} while (p[i] <= n);
printf("%d %d", p[i-1], p[i]);
return 0;
}
int fibo(int i) {
if (i == 0) {
return 0;
} else
if (i == 1) {
return 1;
} else {
return (fibo(i - 1) + fibo(i - 2));
}
}
这是我写的程序。我得到了一个完全垃圾的答案。有人可以帮我解决我哪里出错了吗?
您将数组元素与刚刚计算的元素进行比较。数组未初始化,行为未定义。
您可以这样修复您的代码:
int main() {
int n, p[100];
scanf("%d", &n);
int i = 0;
do {
p[i] = fibo(i);
i++;
} while (p[i-1] <= n);
printf("%d %d", p[i-2], p[i-1]);
return 0;
}
但是你的代码有几个小问题:
- 您不检查
scanf()
是否成功。
- 将值存储到
p
数组时不检查是否存在潜在的缓冲区溢出。
- 对于较小的
n
值,您有未定义的行为,因为您将以负偏移量读取 p
的条目。
这是解决这些问题的更正版本:
#include <stdio.h>
int fibo(int);
int main(void) {
int n, p[100];
if (scanf("%d", &n) == 1) {
for (int i = 0; i < 100; i++) {
p[i] = fibo(i);
if (p[i] > n)
break;
}
if (i >= 2) {
printf("%d %d\n", p[i - 2], p[i - 1]);
}
}
return 0;
}
int fibo(int i) {
if (i == 0) {
return 0;
} else
if (i == 1) {
return 1;
} else {
return (fibo(i - 1) + fibo(i - 2));
}
}
但请注意,Fibonacci 序列发散很快,并且可能会发生算术溢出,从而导致未定义的行为,从而为较大的 n
产生不正确的结果。
这里有一个更简单的解决方案,不使用递归并且没有这个问题:
#include <stdio.h>
int main(void) {
int n, a = 0, b = 1;
if (scanf("%d", &n) == 1 && n > 1) {
while (a < n - b) {
int c = a + b; /* no overflow possible */
a = b;
b = c;
}
printf("%d %d\n", a, b);
}
return 0;
}