shで計算

ウノウラボ Unoh Labs: シェルスクリプトでプログラミングを読んで、少し遊びたくなった。

シェルスクリプトで演算を行うにはexprを使います。

add.sh

#!/bin/sh
A=1
B=2
C=`expr ${A} + ${B}`
echo ${C}

確かに、教科書的にはexprだろう。
そもそも、Linuxcygwinなど、多くのUN*X系OSやUN*Xっぽい環境では、shはbashのaliasだったりするはず。
# FreeBSD(PC-BSD)のshはshのようだけど…。

で、bash環境下では、$(())で計算が出来る。
当然、zsh環境下でも使える。

Owner@fam ~ $ sh --version
GNU bash, version 3.2.39(19)-release (i686-pc-cygwin)
Copyright (C) 2007 Free Software Foundation, Inc.
Owner@fam ~ $ sh -c "echo $((1+2*3))"
7

csh系では別の書き方をする。

%@ x = 1 + 2 * 3; echo $x
7

素のshでは、スペースの位置に気をつけなければならないけど、同じ動きをする。

[pcbsd@pcbsd ~]$ sh -c "echo $(( 1 + 2 * 3 ))"
7

で、整数演算しか出来ないのはまぁ、ご愛嬌というか…。

Owner@fam ~ $ sh -c "echo $((1.0+1.0))"
bash: 1.0+1.0: syntax error: invalid arithmetic operator (error token is ".0+1.0")

とはいえ、exprを使うより速度はだいぶ違う事は、覚えておいてもいいのではないか。

Owner@fam ~ $ time for ((i=0;i<100;i=i+1)); do x=`expr 1 + 2`; done

real    0m3.903s
user    0m2.470s
sys     0m1.060s
Owner@fam ~ $ time for ((i=0;i<100;i=i+1)); do x=$((1+2)); done

real    0m0.030s
user    0m0.000s
sys     0m0.000s

当然大昔の環境だとこの技は使えないだろうけど、そろそろソコは無視しても良いのではないだろうか。

sed

sedはテキストデータを置換するのによく使われるプログラムです。例えば、先程のbokko.txtの全ての行をbokkoに置換してみましょう。

$ cat bokko.txt | sed -e 's/bok\+o/bokko/g' | uniq
bokko
$

いまどきのbashは置換もできる。

Owner@fam ~ $ x=(`cat bokko.txt`); for ((i=0;i<${#x[*]};i++)); do echo ${x[$i]/bok*o/bokko}; done | uniq -c
     24 bokko

(実は s/bok.*o/bokko/gなのは秘密)
いや一般向けにこんなの解説するのはどうかと思うから、コレでいいのだけど。