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.导致此错误的原因是什么?
答案 0 :(得分:7)
函数返回值最多只能达到255:
a()
{
return 255
}
a
echo $?
b()
{
return 256
}
b
echo $?
产地:
$ bash x.sh
255
0
return
与exit
类似,exit
只能获取最多255(http://www.unix.org/whitepapers/shdiffs.html)的值。
另一种选择是切换到迭代建议,如另一个答案中所述。 或者,您可以使用echo并以这种方式捕获递归输出:
#!/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 :(得分: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"
答案 2 :(得分:2)
您所看到的是256处函数返回值的回绕。720 mod 256
是208
(256 + 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
12201368259911100687012387854230469262535743428031928421924135883858
45373153881997605496447502203281863013616477148203584163378722078177
20048078520515932928547790757193933060377296085908627042917454788242
49127263443056701732707694610628023104526442188787894657547771498634
94367781037644274033827365397471386477878495438489595537537990423241
06127132698432774571554630997720278101456108118837370953101635632443
29870295638966289116589747695720879269288712817800702651745077684107
19624390394322536422605234945850129918571501248706961568141625359056
69342381300885624924689156412677565448188650659384795177536089400574
52389403357984763639449053130623237490664450488246650759467358620746
37925184200459369692981022263971952597190945217823331756934581508552
33282076282002340262690789834245171200620771464097945611612762914595
12372299133401695523638509428855920187274337951730145863575708283557
80158735432768888680120399882384702151467605445407663535984174430480
12893831389688163948746965881750450692636533817505547812864000000000
00000000000000000000000000000000000000000000000000000000000000000000
00000000000000000000000000000000000000000000000
我很想看到bash
- 唯一解决方案计算500的阶乘: - )
答案 3 :(得分:1)
有趣的是,该程序使用破折号按预期工作,它只使用bash失败。所以看起来这是一种基础。
只需添加一行
即可#!/bin/dash
在程序的顶部,它可以工作!
答案 4 :(得分:1)
Bash脚本和Bash函数返回值旨在返回代码,因此受限于它们能够返回的值。您不应该依赖于127之前的值(通常是更大的值,然后是127 - 最多255 - 用于表示收到的信号)。
行
fact $y
b=$(($1 * $?))
期望使用$?
的返回码fact
,并且此代码不能更高,然后是255。
返回值的Bash方式是打印它们,并解析或评估此输出。