2016-09-29 6 views
0

今日、私のシェルスクリプトが時折早く終了することがわかりました。コードを確認した後、シェルスクリプトの先頭にset -eがあり、組み込み関数RANDOMを使って乱数を生成していることがわかります。シェル - 組み込みのRANDOM関数が1を返すのはなぜですか?

set -eで、スクリプト内のコマンドが0以外の値を返した場合、スクリプトはすぐに終了します。だから私はこのようなテストコードのスニペットを書く:

set -u 
#set -e 

for ((i=0; i < 100; i++)) 
do 
index=$(expr ${RANDOM} % 16) 
echo "RANDOM return $? , index is $index" 
done 

ご注意くださいコメントset -eに、私はなるようにすると、いくつかのRANDOM return 1が実際に存在する100の出力ラインを表示することを行います。たとえば、次のような結果が得られます。

RANDOM return 0 , index is 2 
RANDOM return 0 , index is 10 
RANDOM return 1 , index is 0 
RANDOM return 0 , index is 9 
RANDOM return 0 , index is 5 
RANDOM return 0 , index is 9 
RANDOM return 0 , index is 4 
RANDOM return 0 , index is 6 
RANDOM return 0 , index is 2 
RANDOM return 0 , index is 4 
RANDOM return 0 , index is 14 
RANDOM return 0 , index is 6 
RANDOM return 0 , index is 2 
RANDOM return 1 , index is 0 
RANDOM return 0 , index is 1 
RANDOM return 0 , index is 8 
...(more line) 

参照してください。 RANDOMは1を返しますが、乱数を正しく生成します。そのため、シェルスクリプトが早期に終了するのはそのためです。 Pythonの乱数生成コードに切り替えると、スクリプトは正常に戻ります。

なぜRANDOMが1を返しますか?

+0

演算には 'expr'を使用しないでください。 'index = $(($ RANDOM%16))'を使ってください。 – chepner

答えて

7

$?は、実行した最後のコマンドのステータスです。 $RANDOMはコマンドではないため、評価すると$?には影響しません。 ($RANDOMは、それが評価されていますとき0と32767の間のランダムな整数を生成する「シェルパラメータ」または変数である。)

あなたが見ている$?値はコマンドexpr ${RANDOM} % 16を実行した結果です。式の評価結果が0 nullの場合、または$RANDOM % 16は0(時間の6.25%)である時はいつでもあなたが1の状態を取得しますので、

exprコマンドは、1の状態を返します。あなたがset -eをやったし、シェルを終了せずに失敗することがありますコマンドを実行したい場合は

% expr 1 % 16 ; echo "\$?=$?" 
1 
$?=0 
% expr 0 % 16 ; echo "\$?=$?" 
0 
$?=1 

、あなたは|| trueのようなものを追加することができます。 ||の接頭辞が条件として使用されるため、失敗すると条件がfalseになります。

index=$(expr ${RANDOM} % 16) || true 
echo "Status of expr is $?, index is $index" 
関連する問題