ここには2つの問題があります。まず、すべての変数はグローバルです。つまり、再帰呼び出しを行うと、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より大きくなることはできません(その後、0にラップアラウンドします)。実際に成功/失敗の結果(何が失敗したかについての情報)を与えることを意図しています。 。0何か他のものは、トラブルを求めているためにそれを使用しようとするとエラーを示す成功と何かを示すあなたは(機能のlocal
化さバージョンから)ここでの結果を見ることができます:。
$ fib 11; echo $?
89
$ fib 12; echo $?
144
$ fib 13; echo $?
233
$ fib 14; echo $?
121
14日フィボナッチ数377ですが、それは255を超えていますので、377-256 = 121として出てきました。これを修正するには、echo
で結果を返し、$()
:
...しかし、これは非常に遅いです。fib
へのすべての呼び出しはサブプロセスとして実行する必要があり、サブプロセスを作成するには計算コストがかかるためです。 (これは実際には変数がサブプロセスに継承されるが、それらからは継承されないため、グローバル変数問題は解決されていますが、偶然にのみ解決されます)
Take-homeレッスン:シェルスクリプトは正しくありませんこのようなことのための言語。
それは
awk
のようなもので道に簡単です
関連:http://stackoverflow.com/q/17336915/632407 – jm666