忘備録

日々の調べ物をまとめる。アウトプットする。基本自分用。

【ShellScript】基本的なこと

コメント

#から行末までがコメントとみなされる

例)

$ echo Hello World #comment
Hello World

注意すべきこと

  • 行頭以外にコメントを書く場合、#の直前に区切り文字(スペース、タブ)が必要
  • [改行]を利用し、コマンドを継続している行にはコメントは書けない

例)

$ echo Hello World#comment
Hello World#comment
# #の直前はスペースがないとコメントにならない
$ echo Hello \
>World
Hello World
# Hello \の後にコメントは挿入不可
# Worldの後は可
$ echo Hello \
>World #comment
Hello World

フォーマット

フリーフォーマットのため以下のことができる

  • 行頭にスペースやタブを入力できる
  • 制限があるが任意の位置で改行できる

例)

for var in hoge fuga piyo
do
    echo "$var" #スペースやタブでインデントを調整できる
done

# \と合わせることで任意の位置に改行を含めることができる
echo Hello \
World

# |などパイプラインの途中であることが分かる入力の後であれば改行を含めることができる
for var in hoge fuga piyo
do
    echo "$var"
done |
grep piyo # |の後で改行されているため、コマンドは実行されず、grepの標準入力にhoge fuga piyoが渡される

実行結果

hoge
fuga
piyo
Hello World
piyo

用語

組込みコマンド(内部コマンド)

使用頻度が高い重要なコマンドや、原理的に外部コマンドにできないためシェルに組み込まれているコマンド

外部コマンド

組み込みコマンド以外のコマンド

※ typeコマンドを利用することで外部コマンドか内部コマンドか調べることができる

$ type cd
cd is a shell builtin #組み込みコマンド
$ type cp
cp is /bin/cp #外部コマンド

複合コマンド

以下のコマンドのこと

  • if, case, for, whileなどの構文
  • サブシェル
  • グループコマンド
  • シェル関数

単純コマンド

一般的なUNIXコマンドのこと

複合コマンド以外のコマンドは単純コマンド

終了ステータス

コマンドの成否を表す数値。

終了ステータス 真偽値
0
0以外

なお、特殊変数「$?」で参照できる。

例)

$ cd /hoge/
-bash: cd: /hoge: No such file or directory
$ echo $?
1 #コマンドの引数に不正な値を与えたので0以外が返される
$ cd /usr/
$ echo $?
0 #正常終了したので0が返される

パイプライン

コマンドの標準出力を別コマンドの標準入力に接続すること

  • |(パイプ)によって区切ることでパイプラインを構成する
  • 単純コマンドだけでなくfor文や、サブシェルなどでもパイプラインを構成できる
  • シェルの文法上、コマンド1つ(パイプなし)でもパイプラインと呼ぶ

例)

# カレントディレクトリにある拡張子が.txtのものだけを出力
ls | grep .*\.txt

# 複合コマンドに対してもパイプラインを構成できる
for param in hoge fuga piyo
do
    echo "$param"
done | grep .*e #hogeが出力される

# 文法上はコマンド単体でもパイプラインらしい
ls #こいつもパイプライン

リスト

1つ以上のパイプラインを改行などで区切って並べたもの

  • 改行のほかに「;」、「&」、「&&」、「||」も区切りとして使用できる
  • 改行、「;」「;&」はリストの終端を表す

例)

cd /Users/makoto; ls -l #cdとlsという2つのパイプラインが「;」で区切られ1つのリストになっている

サブシェル

リストをまとめて別シェルで実行する。

例)

(cd ~/Documents; pwd)

実行結果

/Users/makoto/Documents

グループコマンド

リストを1つのコマンドとして実行する。

例)

{ cd ~/Documents; pwd; }

実行結果

/Users/makoto/Documents

※ サブシェルとグループコマンドの違い

  • サブシェルは別プロセスで処理される
  • グループコマンドは同一プロセスで処理される

例)

#Group Command
GCMSG='GCMSG: before'
{ GCMSG='GCMSG: after'; }
echo "$GCMSG"

#Sub Shell
SSMSG='SSMSG: before'
(SSMSG='SSMSG: after')
echo "$SSMSG"

実行結果

GCMSG: after
SSMSG: before

シェル関数

一定の処理を関数としてまとめる

例)func.sh

myFunc()
{
    for arg in "$@"
    do
        echo "$arg"
    done
}

#シェル関数の呼出し(hoge fuga piyoは引数)
myFunc hoge fuga piyo

実行結果

hoge
fuga
piyo