バッシュの乗算と加算


18
for k in {0..49};
do
a=$(($((2*$k))+1));
echo $a;
done

こんにちは、3行目の簡略化された式が必要です。おそらく、コマンド置換を使用しない式です。


@Theophrastus:示唆されたように、うまく動作しますが、(())の代わりにexprを使用したい場合はどうでしょう。
AVS

これはそうではbashありませんCので、すべて削除してください;-単数行で記述しない限り。
ott--


declare -i a; for k in {0..49}; do a=2*$k+1; echo $a; done
サイラス

1
余談:$(( ... ))算術展開はコマンド置換ではありません。
dave_thompson_085

回答:


27

算術展開の使用:

for (( k = 0; k < 50; ++k )); do
  a=$(( 2*k + 1 ))
  echo "$a"
done

時代遅れのexprユーティリティの使用:

for (( k = 0; k < 50; ++k )); do
  a=$( expr 2 '*' "$k" + 1 )
  echo "$a"
done

使用bc -l-l数学関数が使用されていないため、この場合は実際には必要ありません):

for (( k = 0; k < 50; ++k )); do
  a=$( bc -l <<<"2*$k + 1" )
  echo "$a"
done

bc -lコプロセスとして使用する(バックグラウンドで一種の計算サービスのように動作します¹):

coproc bc -l

for (( k = 0; k < 50; ++k )); do
  printf "2*%d + 1\n" "$k" >&${COPROC[1]}
  read -u "${COPROC[0]}" a
  echo "$a"
done

kill "$COPROC_PID"

最後の1つは(ほぼ間違いなく)よりきれいに見えますksh93

bc -l |&
bc_pid="$!"

for (( k = 0; k < 50; ++k )); do
  print -p "2*$k + 1"
  read -p a
  print "$a"
done

kill "$bc_pid"

¹これにより、一度に大量の入力をループで処理する必要があるという問題が解決しました。処理にはいくつかの浮動小数点計算が必要でしたbcが、ループ内での数回の生成は非常に遅いことが判明しました。はい、他の多くの方法で解決できたかもしれませんが、退屈していました...



5

このletコマンドを使用して、計算を強制できます。

let a="2*k+1"

$kこの構造では必要ないことに注意してください。単純なものkが仕事をします。


4
a=2whateverk+1現在のディレクトリにファイルが呼び出されている場合、失敗します。さらに悪いことに、コマンドa=2+b[$(reboot)]k+1を呼び出すというファイルが存在する場合reboot。ベストは、使用することです((...))(ここでは((a = 2 * k + 1)))、またはPOSIXの構文:a=$((2 * k + 1))
ステファンChazelas

引用できます。let a="2*k+1"それを解決します。
スティーブンハリス

2

おそらく必要な算術展開は次のとおりです。

a=$(( 1+2*k ))

実際、変数を使用する必要はありません。

for k in {0..49}; do
    echo "$(( 1 + 2*k ))"
done

または、カウント変数をfor ((…))ループに移動できます。

for (( k=0;k<50;k++ )); do
    a=$(( 1+2*k ))
    printf '%s\n' "$a"
done

for((…))ループ

また、その場合、算術展開はforループ内に移動することもできます。

for (( k=0 ; a=1+2*k , k<50 ;  k++)); do
    printf '%s\n' "$a"
done

または、配列内のすべての値を取得するには:

for (( k=0 ; a[k]=1+2*k , k<49 ;  k++ )); do :; done
printf '%s\n' "${a[@]}"

数式なし

しかし、おそらく算術展開を回避する最も簡単な方法は、変数を2回インクリメントすることです。

for (( k=0,a=1 ; k<50 ;  k++,a++,a++ )); do
    printf '%s\n' "$a"
done

または、さらに簡単に、単にseqを使用します。

seq 1 2 100
弊社のサイトを使用することにより、あなたは弊社のクッキーポリシーおよびプライバシーポリシーを読み、理解したものとみなされます。
Licensed under cc by-sa 3.0 with attribution required.