当我将4000000放入方法的参数大小,即fib(4000000)时,我不确定为什么我的代码会产生错误的负值?
问题是:
Fibonacci序列中的每个新术语都是通过添加前两个术语生成的。从1和2开始,前10个术语将是:
1,2,3,5,8,13,21,34,55,89,......
通过考虑Fibonacci序列中的值不超过四百万的项,找到偶数项的总和。
我的第一个代码:
public void fib(int k) {
int result = 0;
int[] array = new int[k];
array[0] = 1;
array[1] = 2;
for (int i = 2; i < k; i++) {
array[i] = array[i - 2] + array[i - 1];
}
for (int even: array) {
if (even % 2 == 0) {
result += even;
}
}
System.out.println(result);
}
哪个没有用,所以我认为这是因为数组大小太大(四百万很多)所以我试着写一个不同的代码:
public void fib(int k) {
int sum = 0;
int term1 = 1;
int term2 = 2;
int term3 = 0;
int i = 2;
while (i < k) {
term3 = term1 + term2;
term1 = term2;
term2 = term3;
i++;
if (term2 % 2 == 0) {
sum += term2;
}
}
System.out.println(sum + 2);
}
哪个也没有用。
我的代码出了什么问题?对于少数size
它可以工作,但是对于它来说它不起作用。
在我搜索了我发现的问题的答案之后:
int term1 = 1;
int term2 = 2;
int i = 0;
int result = 0;
while (term1 < 4000000) {
i = term1;
term1 = term2;
term2 = term2 + i;
if (term2 % 2 == 0) {
result += term2;
}
}
System.out.println(result);
有效。
答案 0 :(得分:4)
我认为你不会遇到溢出问题。我认为你的问题有点不正确。它说你应该查看所有斐波那契数字,其中数字的值<= 4百万。相反,你正在查看前400万斐波那契数字。这是它之间的区别:
1,2,3,5,8(所有纤维数小于10)
和此:
1,2,3,5,8,13,21,34,55,89(前10个纤维数)
我认为它需要前者,但你正在做后者。
而不是:
while (i < k) {
如果你这样做怎么办?
while (term1 < k) {
答案 1 :(得分:3)
根据doc:
默认情况下,int数据类型是32位带符号的二进制补码 整数,最小值为-2 ^ 31,最大值为 2 ^ 31-1。
您将总和存储在result
中,这是一个int,它将溢出。如下所示,重新获得它,它将起作用:
public static void fib(int size) {
long result = 0;
int[] array = new int[size];
array[0] = 1;
array[1] = 2;
for (int i = 2; i < size; i++) {
array[i] = array[i - 2] + array[i - 1];
}
for (int even: array) {
if (even % 2 == 0) {
result += even;
}
}
System.out.println(result);
}
fib(4000000)
的值现在为2111290219918
。签名的long的最小值为-2^63
,最大值为2^63-1
。