シェル言語

シェル言語

長い話を短く

私はこれについていくつかの調査を行いました、あなたは私がしたことを見ることができます詳細と私の試み部分。

私のコマンドは

date && echo "hi 1" && echo "1/0" | bc >/dev/null 2>&1 && echo "hi 2" && date +'%s'

私の予想/必要な出力は次のとおりです。

Tue, Nov 17, 2020  3:13:49 PM
hi 1

そして止めてください。私の考えは式の「echo/ bc」部分です(作業優先順位が括弧で示されていると仮定)

<part-before> echo "1/0" | bc >/dev/null 2>&1 ) && <part-after>

<part-after>目的が達成されないようにしてください。しかし、私実際出力(date現在のコマンドを使用)は次のとおりです。

Tue, Nov 17, 2020  3:13:49 PM
hi 1
hi 2
1605651229

質問:何も出力せずに失敗し、ゼロで割る問題で停止するにはどうすればよいですか?


(以降の内容は、より詳細な内容を提供するためのものです。)

クイックノート:リダイレクトがない場合でもゼロで割り切ることができなくても、チェーン、&&つまり短絡されたAND演算子チェーンは停止しません。より、

bballdave025@MACHINE ~
$ date && echo "hi 1" && echo "1/0" | bc && echo "hi 2" && date +'%s'
Tue, Nov 17, 2020  3:14:47 PM
hi 1
Runtime error (func=(main), adr=3): Divide by zero
hi 2
1605651287

bballdave025@MACHINE ~
$

bc私は主に$(( ))以下のようなbash-ismを避けるためにこの方法を使いたいと思います。 (bash-ismsについて言えば、努力しても&>/dev/null何も変わりませんでした。)以下の例のようなものを手に入れたいです。

bballdave025@MACHINE ~
$ date && echo "hi 1" && echo "$((1/0))" >/dev/null 2>&1 && echo "hi 2" && date +'%s'
Tue, Nov 17, 2020  3:15:17 PM
hi 1
-bash: 1/0: division by 0 (error token is "0")

bballdave025@MACHINE ~
$

しかし、私はエラーを望んでいません。 0で割った誤った結果が出力されない限り、つまり-edがなければechoエラーを取り除くことができます(これはリダイレクトの目的を崩します。stdoutstderr

### NOT WHAT I WANT, other than what is output ###
bballdave025@MACHINE ~
$ date && echo "hi 1" && ((1/0)) >/dev/null 2>&1 && echo "hi 2" && date +'%s'
Tue, Nov 17, 2020  3:15:44 PM
hi 1

bballdave025@MACHINE ~
### NOT WHAT I WANT, other than what is output. ###

より理論的な説明は次のとおりです。に0(ゼロ)を渡しています&&。何ですか?

私は見つけたこのソースアーカイブ)、すなわち

リダイレクトはコマンドではありません。

今はどこを見るべきかわかりません。


編集する:もう少し調べてみました。 2つの点を追加したい。

  1. 複数のソースが見つかりました。それらの一つアーカイブ)これはコアかもしれないと思いますが、それがどのように適用されるかはまだ理解されていません。その他アーカイブ)段落について説明しますが、これが重要であると考えられています。

  2. >/dev/null誤って交換したときに奇妙な動作が見つかり、バグが>dev/null発生しました。後ろに問題をゼロで割ります。これが私が見るものです。

bballdave025@MACHINE ~
$ a=1; b=1; c=0; date && echo "hi 1" && echo "$a/$b" | bc >dev/null 2>&1 && echo "hi 2" && date +'%s'
Tue, Nov 17, 2020  3:41:39 PM
hi 1
-bash: dev/null: No such file or directory

bballdave025@MACHINE ~
$ a=1; b=1; c=0; date && echo "hi 1" && echo "$a/$c" | bc >dev/null 2>&1 && echo "hi 2" && date +'%s'
Tue, Nov 17, 2020  3:41:48 PM
hi 1
-bash: dev/null: No such file or directory

bballdave025@MACHINE ~
$

正直なところ、これは特に最初の、おそらくコアソースを考慮すると、より混乱しています。


詳細と私の試み

私はより大きな実行可能ファイルを含むより長いチェーンを構築するために&&チェーンとリダイレクトを理解しようとしています。/dev/null私も知りたいコマンドリスト区切り記号アーカイブ)一般的に言えば、これらの実行可能ファイルがどのように連携するかに関係なく、ここで何が起こっているのかを本当に理解したいと思います&&

私は実際の例に進む前にこのおもちゃの例に取り組んできました。私は問題を見つけることができるかどうかを確認するために「戻る作業」しようとしてきました。おそらくこれは問題を解決するのに役立ちます。

bballdave025@MACHINE ~
$ a=1; b=1; c=0; date && echo "hi 1" && echo "$a/$b" | bc >/dev/null 2>&1 && echo "hi 2" && date +'%s'
Tue, Nov 17, 2020  3:16:41 PM
hi 1
hi 2
1605651401

bballdave025@MACHINE ~
$ a=1; b=1; c=0; date && echo "hi 1" && echo "$a/$c" | bc >/dev/null 2>&1 && echo "hi 2" && date +'%s'
Tue, Nov 17, 2020  3:16:52 PM
hi 1
hi 2
1605651412

## LET'S SEE WHAT GETS SENT TO /dev/null

bballdave025@MACHINE ~
$ a=1; b=1; c=0; date && echo "hi 1" && echo "$a/$b" | bc >abc 2>&1 && echo "hi 2" && date +'%s'
Tue, Nov 17, 2020  3:17:06 PM
hi 1
hi 2
1605651426

bballdave025@MACHINE ~
$ cat abc
1

bballdave025@MACHINE ~
$ a=1; b=1; c=0; date && echo "hi 1" && echo "$a/$c" | bc >abc 2>&1 && echo "hi 2" && date +'%s'
Tue, Nov 17, 2020  3:17:18 PM
hi 1
hi 2
1605651438

bballdave025@MACHINE ~
$ cat abc
Runtime error (func=(main), adr=3): Divide by zero

## LET'S TRY GIVING IT ANOTHER ERROR RIGHT AFTER

bballdave025@MACHINE ~
$ a=1; b=1; c=0; date && echo "hi 1" && echo "$a/$b" | bc >dev/null 2>&1 && echo "hi 2" && date +'%s'
Tue, Nov 17, 2020  3:24:35 PM
hi 1
-bash: dev/null: No such file or directory

bballdave025@MACHINE ~
$ a=1; b=1; c=0; date && echo "hi 1" && echo "$a/$c" | bc >dev/null 2>&1 && echo "hi 2" && date +'%s'
Tue, Nov 17, 2020  3:25:00 PM
hi 1
-bash: dev/null: No such file or directory

bballdave025@MACHINE ~
$ a=1; b=1; c=0; date && echo "hi 1" && echo "$a/$b" | bc >abc 2>&1 && echo "hi 2" && date +'%s'
Tue, Nov 17, 2020  3:25:14 PM
hi 1
hi 2
1605651914

bballdave025@MACHINE ~
$ cat abc
1

bballdave025@MACHINE ~
$ a=1; b=1; c=0; date && echo "hi 1" && echo "$a/$c" | bc >abc 2>&1 && echo "hi 2" && date +'%s'
Tue, Nov 17, 2020  3:25:24 PM
hi 1
hi 2
1605651924

bballdave025@MACHINE ~
$ cat abc
Runtime error (func=(main), adr=3): Divide by zero

bballdave025@MACHINE ~
$ a=1; b=1; c=0; date && echo "hi 1" && echo "$a/$b" | bc >abc/def 2>&1 && echo "hi 2" && date +'%s'
Tue, Nov 17, 2020  3:25:41 PM
hi 1
-bash: abc/def: Not a directory

bballdave025@MACHINE ~
$ a=1; b=1; c=0; date && echo "hi 1" && echo "$a/$c" | bc >abc/def 2>&1 && echo "hi 2" && date +'%s'
Tue, Nov 17, 2020  3:25:46 PM
hi 1
-bash: abc/def: Not a directory

## GO BACK WITHOUT `bc` and without redirection

bballdave025@MACHINE ~
$ a=1; b=1; c=0; date && echo "hi 1" && echo "$a/$b" >/dev/null 2>&1 && echo "hi 2" && date +'%s'
Tue, Nov 17, 2020  3:29:03 PM
hi 1
hi 2
1605652143

bballdave025@MACHINE ~
$ a=1; b=1; c=0; date && echo "hi 1" && echo "$a/$c" >/dev/null 2>&1 && echo "hi 2" && date +'%s'
Tue, Nov 17, 2020  3:29:12 PM
hi 1
hi 2
1605652152

bballdave025@MACHINE ~
$ a=1; b=1; c=0; date && echo "hi 1" && echo "$a/$b" >abc 2>&1 && echo "hi 2" && date +'%s'
Tue, Nov 17, 2020  3:29:21 PM
hi 1
hi 2
1605652161

bballdave025@MACHINE ~
$ cat abc
1/1

bballdave025@MACHINE ~
$ a=1; b=1; c=0; date && echo "hi 1" && echo "$a/$c" >abc 2>&1 && echo "hi 2" && date +'%s'
Tue, Nov 17, 2020  3:29:29 PM
hi 1
hi 2
1605652169

bballdave025@MACHINE ~
$ cat abc
1/0

bballdave025@MACHINE ~
$ a=1; b=1; c=0; date && echo "hi 1" && echo "$a/$b" && echo "hi 2" && date +'%s'
Tue, Nov 17, 2020  3:30:09 PM
hi 1
1/1
hi 2
1605652209

bballdave025@MACHINE ~
$ a=1; b=1; c=0; date && echo "hi 1" && echo "$a/$c" && echo "hi 2" && date +'%s'
Tue, Nov 17, 2020  3:30:14 PM
hi 1
1/0
hi 2
1605652214

bballdave025@MACHINE ~
$ a=1; b=1; c=0; date && echo "hi 1" && echo "hi 2" && date +'%s'
Tue, Nov 17, 2020  3:30:26 PM
hi 1
hi 2
1605652226

bballdave025@MACHINE ~
$

このSO交換アーカイブ)役に立つものがあるかもしれません。

ベストアンサー1

リダイレクトがなくてもゼロで除算できない場合でも、「and」演算子の段落チェーン&&チェーンは停止しません。

GNU BC:

$ echo "1/0" | bc 
Runtime error (func=(main), adr=3): Divide by zero
$ echo $?
0

忙しい箱:

$ echo "1/0" | busybox bc 
bc: divide by zero
$ echo $?
1

POSIX BC:

名前
bc - 任意精度算術言語の
終了状態
次の終了値を返す必要があります。
0 - すべての入力ファイルが正常に処理されました。
指定しない - エラーが発生しました。

根拠
エラー条件の終了状態は、いくつかの理由で指定されません。

  • bcユーティリティは、対話型状況と非対話型状況の両方で使用できます。両方の目的に異なる終了コードが適している可能性があります。
  • ゼロ以外の出口がいつ提供されるべきかは明確ではない。ゼロ除算、未定義関数、および構文エラーの両方が可能です。
  • 終了状態がどの用途に使用されるかは不明です。

BCはゼロで割ることが間違った終了状態を返す価値がないと思うので、チェーンは壊れません。

ただし、GNU bc は、入力ファイルを読み取れない場合、無効な終了状態を返します。

私は主に後で$(())のようなbash-ismsを避けるためにbcメソッドを使用したいと思います。

$(( ))バシズムではなくバシズムの一部POSIXシェル言語(算術拡張)


&&ここでの文脈が何であるか、ゼロで割ることが条件やチェーンとどのように関連するのか、最終的に何をしたいのか分からないので、アドバイスを提供することは困難です。

ゼロで除算を検出する別の方法は、まず、除算を試みる前に除算がゼロであることを確認することです。

おすすめ記事