2010-08-03 53 views
3
fact() 
{ 
    if [ $1 -eq 1 ] 
    then 
     return 1 
    else 
     y=`expr $1 - 1` 
     fact $y 
     b=$(($1 * $?)) 
     return $b 
    fi 
} 
echo "enter" 
read n 
fact $n 
echo "$?" 

這是一個程序來查找一個數字的階乘。輸出是正確的最多5.輸出6是給208,但正確的答案是720.什麼導致這個錯誤?爲什麼我的bash函數返回錯誤的值?

+0

可能重複的階乘[你如何在Bash腳本中找到數字的階乘?](http://stackoverflow.com/questions/3394580/how-do-you-find-the-factorial-of-a-number-in- a-bash腳本) – 2010-08-03 13:39:59

回答

7

函數的返回值只能上升到255:

a() 
{ 
     return 255 
} 

a 
echo $? 

b() 
{ 
     return 256 
} 

b 
echo $? 

產地:

$ bash x.sh 
255 
0 

return就像exitexit只能採取值高達255(http://www.unix.org/whitepapers/shdiffs.html)。

一種替代方法是切換到迭代建議,如另一個答案中所述。 或者您可以使用回聲和捕捉遞歸輸出方式:

#!/bin/bash 

fact() 
{ 
    if [ $1 -eq 1 ] 
    then 
     echo 1 
    else 
     y=$(expr $1 - 1) 
     f=$(fact $y) 
     b=$(($1 * $f)) 
     echo $b 
    fi 
} 
echo "enter" 
read n 
fact $n 
1

有趣的是,在使用虛預期的程序工作,它只是無法使用bash。所以看起來這是一種抨擊。

只需添加一行

#!/bin/dash 

在程序的頂部和它的作品!

+0

好奇心+1。不過,我預計它會再次突破一些稍大的數字。 – tripleee 2013-05-27 16:44:58

2

bourne shell不能在$存儲嗎? (退出代碼)。限制爲255。下面有一個替代的方式

n=0 
on=0 
fact=1 

echo -n "Enter number to find factorial : " 
read n 

on=$n 

while [ $n -ge 1 ] 
do 
    fact=`expr $fact \* $n` 
    n=`expr $n - 1` 
done 

echo "Factorial for $on is $fact" 
1

Bash腳本和Bash函數返回值都旨在被返回代碼,並因此限制與它們能夠返回的值。您不應該依賴於127以上的值(通常127以上的值 - 最多255)用於指示接收到的信號。

線條

fact $y 
b=$(($1 * $?)) 

希望使用$?fact返回代碼,而這種代碼不能被擦菜板則255

返回值的Bash的方式打印和解析或評估這個輸出。

2

你所看到的是函數返回值在256處的環繞。720 mod 256208256 + 256 + 208 = 720)。

我的建議是,如果你必須使用shell功能,就是要做到:

#!/bin/bash 
fact() 
{ 
    if [ "$1" -eq "1" ] 
    then 
     echo 1 
     return 
    fi 
    y=`expr $1 - 1` 
    z=$(fact $y) 
    echo $(($1 * $z)) 
} 
echo "enter" 
read n 
echo "$(fact $n)" 

它使用標準輸出返回值,而不是返回代碼。

,或者甚至更好,使用權工具的作業:

pax> echo 'define f(x) {if (x>1){return x*f(x-1)};return 1} 
      f(6)' | bc 
720 
pax> echo 'define f(x) {if (x>1){return x*f(x-1)};return 1} 
      f(500)' | BC_LINE_LENGTH=99999 bc 
12201368259911100687
45373153881997605496447502203281863013616477148203584163378722078177 
20048078520515932928547790757193933060377296085908627042917454788242 
49127263443056701732707694610628023104526442188787894657547771498634 
94367781037644274033827365397471386477878495438489595537537990423241 
06127132698432774571554630997720278101456108118837370953101635632443 
29870295638966289116589747695720879269288712817800702651745077684107 
19624390394322536422605234945850129918571501248706961568141625359056 
69342381300885624924689156412677565448188650659384795177536089400574 
52389403357984763639449053130623237490664450488246650759467358620746 
37925184200459369692981022263971952597190945217823331756934581508552 
33282076282002340262690789834245171200620771464097945611612762914595 
12372299133401695523638509428855920187274337951730145863575708283557 
80158735432768888680120399882384702151467605445407663535984174430480 
12893831389688163948746965881750450692636533817505547812864000000000 
00000000000000000000000000000000000000000000000000000000000000000000 
00000000000000000000000000000000000000000000000 

我很願意看到一個bash - 只計算解決方案:-) 500

相關問題