打印2个最接近,较小的斐波纳契数

时间:2018-03-13 21:54:01

标签: java fibonacci

我很难找到解决这个问题的方法。我需要编写一个迭代(不能使用递归)解决方案来解决用户通过扫描仪输入数字的问题(例如,10),并打印2个“之前的”Fib数。

对于输入“10”的例子,它将是:

5
8

因为它们是10之前的“最大”两个Fib数。

如果输入为13,则会打印:

8
13

由于13是一个Fib数本身,它只打印1个数字,然后自己打印。

现在我知道如何迭代地找到“第n个”Fib数,但是我无法理解一个解决方案来运行直到给定的数字(而不是第n个Fib数)并以某种方式仅打印在它之前的最后2个(或者,如果给定的数字本身就是一个Fib数,那么也算作一个)。

现在我知道使用完美方块的公式 - 但遗憾的是,不能使用...

编辑,因为它让一些人感到困惑:

我不要求代码,也不希望任何人为我解决这个问题。我只是真的想了解如何处理这些问题。

编辑#2:

这是我写的代码:

int a = 0;
int b = 1;

while (a < num) {
    int temp = a;
    a = a + b;
    b = temp;
}
System.out.println(b);
System.out.println(a);

我遇到的问题是,如果num输入确实是一个Fib数 - 它将按预期工作,否则,它打印1个先前的Fib num和下一个,所以对于输入“10”,它打印8和13。

1 个答案:

答案 0 :(得分:0)

说明

你说你已经有了一个计算迭代n - 斐波那契数的方法。由于Fibonacci数通常是根据最后两个Fibonacci元素定义的,所以你也应该已经有了它们,请参阅维基百科的定义:

Fibonacci definition

您唯一需要做的就是运行迭代方法直到达到输入。然后输出F_(n - 1)F_(n - 2)的当前记忆值(如果等于输入,则输出F_n。)

实施例

假设你有一个斐波纳契方法(我从第一个谷歌搜索结果中获取)

public static long fib(int n) {
    if (n <= 2) {
        return (n > 0) ? 1 : 0;
    }
    long fib1 = 0;
    long fib2 = 1;
    for (int i = 1; i < n; i++) {
        final long newFib = fib1 + fib2;
        fib1 = fib2;
        fib2 = newFib;
    }
    return fib2;
}

您需要对其进行修改以接受input并返回最后一个Fibonacci数字fib1fib2。将循环替换为n的无限循环,超过input

public static long[] fib(long input) {
    // Special cases
    if (input == 1) {
        return new long[] { 1l, 1l };
    }
    if (input == 0) {
        return new long[] { 0l };
    }
    if (input < 0) {
        return null;
    }

    // Seed values
    long fib1 = 0;
    long fib2 = 1;

    // Repeat until return
    while (true) {
        long newFib = fib1 + fib2;

        // Reached the end
        if (newFib >= input) {
            // Push 'newFib' to the results
            if (newFib == input) {
                fib1 = fib2;
                fib2 = newFib;
            }
            return new long[] { fib1, fib2 };
        }

        // Prepare next round
        fib1 = fib2;
        fib2 = newFib;
    }
}

该方法现在在[0]返回到最近的斐波那契,并在[1]返回最近的斐波纳契数到input

您可以使用此示例轻松调整自己的方法。

用法:

public static void main(String[] args) {
    long[] results = fib(20L);
    // Prints "8, 13"
    System.out.println(results[0] + ", " + results[1]);

    results = fib(21L);
    // Prints "13, 21"
    System.out.println(results[0] + ", " + results[1]);
}

另一个例子

使用某种nextFib方法可以获得对同一问题的不同看法。然后你可以反复挑选,直到超过input。因此,我们建立一些类

public class FibonacciCalculator {
    private long fib1 = 0;
    private long fib2 = 1;
    private int n = 0;

    public long nextFib() {
        // Special cases
        if (n <= 2) {
            long result = (n > 0) ? 1 : 0;
            // Increase the index
            n++;
            return result;
        }

        // Compute current and push
        long newFib = fib1 + fib2;
        fib1 = fib2;
        fib2 = newFib;

        return newFib;
    }
}

然后我们调用它直到超过input,始终记住最后两个值:

public static long[] fib(long input) {
    FibonacciCalculator calc = new FibonacciCalculator();
    long lastFib = 0L;
    long secondToLastFib = 0L;

    while (true) {
        long curFib = calc.nextFib();

        if (curFib > input) {
            return new long[] { secondToLastFib, lastFib };
        } else if (curFib == input) {
            return new long[] { lastFib, curFib };
        }

        secondToLastFib = lastFib;
        lastFib = curFib;
    }
}