我试图建立一个递归函数来计算Fibonnaci级数的第n个数。我已经找到了很多解决这个问题的方法,但是我想知道为什么我的方法不起作用。谢谢。
function fib ()
{
if [ $1 -eq 1 -o $1 -eq 2 ]
then
return 1
else
let nr=$1-1
fib $nr
rez1=$?
let nr=$1-2
fib $nr
rez2=$?
let rez=$rez1+$rez2
return $rez
fi
}
最佳答案
这里有两个问题。首先,所有变量都是全局变量,这意味着当您进行递归调用时,它会覆盖nr
、rez
、rez1
和rez2
的值。您可以通过将它们声明为local
来解决此问题:
fib() {
local nr rez rez1 rez2
if [ $1 -eq 1 -o $1 -eq 2 ]; then
return 1
else
let nr=$1-1
fib $nr
rez1=$?
let nr=$1-2
fib $nr
rez2=$?
let rez=$rez1+$rez2
return $rez
fi
}
第二个问题是,您试图通过函数的返回状态传递一个数字。返回状态是一个1字节的无符号整数,这意味着它不能大于255(在255之后,它将返回0)。它的真正目的是给出成功/失败的结果(可能还有一些关于失败的信息),0表示成功,其他任何信息都表示错误。想把它用在别的事情上是自找麻烦。您可以在这里看到结果(从函数的
local
ized版本):$ fib 11; echo $?
89
$ fib 12; echo $?
144
$ fib 13; echo $?
233
$ fib 14; echo $?
121
第14个斐波那契数是377,但超过了255,所以它是377-256=121。要解决此问题,请将结果返回到stdout,并用
echo
捕获它:fib() {
local nr rez rez1 rez2
if [ $1 -eq 1 -o $1 -eq 2 ]; then
echo 1
else
let nr=$1-1
rez1=$(fib $nr)
let nr=$1-2
rez2=$(fib $nr)
let rez=$rez1+$rez2
echo $rez
fi
}
……不过,这确实有一个缺点:它要慢得多,因为对
$( )
的每个调用都必须作为子进程运行,并且创建子进程在计算上非常昂贵。(这实际上解决了全局变量问题,因为变量向下继承到子流程,而不是向上继承;但它只是偶然地解决了这个问题。)带回家的教训:shell脚本不是这样的语言。
关于bash - 生成斐波那契数列的Shell脚本,我们在Stack Overflow上找到一个类似的问题:https://stackoverflow.com/questions/42987607/