在接受采访时我被问到以下问题:
有没有什么方法可以仅使用1个变量生成Fibonacci系列?
我不知道该回答什么。我应该怎么说?
答案 0 :(得分:26)
是的,您可以使用closed-form expression:
,其中
您可以使用double
计算表达式,并将结果四舍五入到最接近的整数。由于浮点运算的精度有限,这个公式将给出足够大的n的错误答案,但我认为它适用于结果适合Java 32位整数的情况。
答案 1 :(得分:18)
一点,是的(虽然在C中,你可以把它转换成Java - 看起来会更加丑陋)。
#include <stdio.h>
#include <stdlib.h>
int main (void) {
unsigned long i = 1;
printf ("0\n");
while (((i & 0xffff0000) >> 16) + (i & 0xffff) <= 0xffff) {
printf ("%d\n", i & 0xffff);
i = ((i & 0xffff) << 16) | ((i >> 16) + (i & 0xffff));
}
return 0;
}
产生:
0
1
1
2
3
5
8
13
21
34
55
89
144
233
377
610
987
1597
2584
4181
6765
10946
17711
28657
: - )
当然,真正的问题是:你为什么要这样做?
如果你对它是如何工作感到好奇,那真的很简单。一个变量实际上分为两部分,这两部分维持Fibonacci序列的各个值。它在技术上仍然是一个变量,我们只是在它上面施加了一些额外的结构来实现我们的目的。
答案 2 :(得分:12)
当然,使用递归:
public class Test {
public static int fib(int n) {
return n < 2 ? n : fib(n-1) + fib(n-2);
}
public static void main(String[] args) {
for(int i = 0; i <= 10; i++) {
System.out.print(fib(i)+", ");
}
System.out.println("...");
}
}
// 0, 1, 1, 2, 3, 5, 8, 13, 21, 34, 55, ...
答案 3 :(得分:4)
是的,但您仍然需要记住2个值。您可以使用64位变量并将其用作2个32位变量。
答案 4 :(得分:4)
答案是“是”,但也许你可能更具体。
我能想到的第一个例子,使用双递归(导致指数复杂,不推荐):
int fib(int a) {
if (a < 2) {
return 1
} else {
return fib(a-1) + fib(a-2);
}
}
假设&gt; = 0(您可以添加一个检查)。
(编辑 - 使用F(0)undefined,F(1)= 1)
的错误约定答案 5 :(得分:3)
在初始1 1
之后,理论上可以通过以下方式从前一个值生成一个值(直到机器精度到来咬你):
f = Math.round(f * PHI)
其中PHI
是另一个评论中定义的常量:
static final double PHI = (1 + Math.sqrt(5))/2;
答案 6 :(得分:3)
您可以随时执行以下操作:
String theOneVar = "100;0;1";
while (true) {
if (theOneVar.split(";")[0].equals("0")) break;
System.out.println(theOneVar.split(";")[1]);
theOneVar = String.format("%s;%s;%s",
Integer.parseInt(theOneVar.split(";")[0]) - 1,
theOneVar.split(";")[2],
new BigInteger(theOneVar.split(";")[1]).add(
new BigInteger(theOneVar.split(";")[2])
)
);
}
0
1
1
2
3
5
8
13
:
:
83621143489848422977
135301852344706746049
218922995834555169026
这只使用一个显式变量,它本质上是一个线性非递归算法。但需要说的是,这是对String
的滥用。
答案 7 :(得分:3)
所以这是邪恶的,但是:
static String fibRecord = "x;";
static int nextFib() {
try {
return fibRecord.indexOf(';');
} finally {
fibRecord = fibRecord.replaceAll("(x*);(x*)", "$1$2;$1");
}
}
public static void main(String[] ignored) {
for (int i=0; i < 30; i++) {
System.out.println(nextFib());
}
}
我的机器开始在第38个斐波那契数字附近摔倒。
答案 8 :(得分:1)
这是C#中的一个例子。显示前100个术语。 Fibonacci中的项之间的比率接近黄金比率(1.618033 ...),因此单个变量方法只需要为每个项乘以常数。
是的数学!
double fib = 1;
for (int i = 0; i < 100; i++)
{
Console.WriteLine("" + fib);
fib = Math.Round(fib *= 1.6180339887d);
}
答案 9 :(得分:1)
class fibo{
public static void main (String args[]) {
long i = 1;
while (((i & 0xffff0000) >> 16) + (i & 0xffff) <= 0xffff) {
System.out.println(i & 0xffff);
i = ((i & 0xffff) << 16) | ((i >> 16) + (i & 0xffff));
}
}
}
这是使用一个变量的Fibonacci系列的java代码。
答案 10 :(得分:0)
该程序最多可打印10个 数字,但你可以改变它。
import java. i o.*;
class q
{
public static void main()throws IO Exception
{
int n=0;
for(int i=1; i<=10 ; i++)
{
System.out.print(n +" ");
n=(int)Math.round(n*1.618)
}
}
}
1.618 = PHI
程序在导入和主要声明中有一些错误,但正文是完全正确的
答案 11 :(得分:0)
public class test {
public static void main(String[] args) {
int arr[]=new int[13];
arr[0]=0;
arr[1]=1;
for(int i=2;i<=12;i++){
arr[i]=arr[i-1]+arr[i-2];
}
for(int i=0;i<=arr.length-1;i++){
System.out.print(arr[i]+" ");
}
}
}