シェルスクリプトではselectという構文が用意されている。
while文とメニュー表示機能が組み合わさったような機能で、シェルスクリプトらしい機能だ。
このページではサンプルプログラムをご紹介しつつ、selectの使い方をまとめてみた。参考にしていただければと思う。
目次
シェルスクリプトのselectとは?
「select」文をつかうと簡易的な対話メニューが簡単に作成できるので便利だ。
丁度while文にメニュー表示機能がまざったような処理をする。メニューを表示しループ処理に入り、変数と分岐処理をつかって制御することが多い。
実際while文と分岐処理を使用し、作り込むと同じようなことができる。しかし若干大がかりになるので素直にselect文を使おう。
これまで解説してきた制御文は「必須の処理」が殆どだったが、今回は「より便利な処理」を実現するため制御文といえる。
なお「select」はbashで追加された制御文でshには対応していない。
selectの書式
次のようになる。
select 変数 in リスト
do
変数に応じた処理
done
Selectのサンプルプログラム
実際にサンプルプログラムと実行結果を見て確認していただくのがわかりやすいだろう。
サンプルプログラム
vi select-ex1.sh
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 |
#!/usr/bin/bash #1) item1 #2) item2 #3) item3 #4) item4 #5) exit #といったメニューが表示される。番号で処理を指定する。 select VAR in item1 item2 item3 item4 exit #doからdoneまでループ処理 do echo "あなたが選んだ項目は$VARです。" #ループから抜けだすための分岐selectで使用したVARを使用する。「5」を選択すれば条件が成立する。 if [ "$VAR" = "exit" ]; then break fi done |
実行結果
$ ./select-ex1.sh
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 |
1) item1 2) item2 3) item3 4) item4 5) exit #? 1 あなたが選んだ項目はitem1です。 #? 2 あなたが選んだ項目はitem2です。 #? 3 あなたが選んだ項目はitem3です。 #? 4 あなたが選んだ項目はitem4です。 #? 5 あなたが選んだ項目はexitです。 |
このように、表示をしつつループを回すのがselectだ。
終了するときにとっさに「exit」と入力しそうになるがexitと打ってもループから抜け出せない。番号を入力しよう。
その他の事柄
もう少しいりくんだサンプル
もう少し難しめの例をご紹介しよう。
vi select-ex2.sh
1 2 3 4 5 6 7 8 9 10 11 |
#!/usr/bin/bash select VAR in pwd ls exit do #繰り返しの中でcase分を使用している。 case $VAR in "ls" ) ls -1 ;; "pwd" ) pwd ;; "exit" ) break ;; * ) echo "あなたの入力した番号は$REPLYです" esac done |
実行結果
$ ./select-ex2.sh
1 2 3 4 5 6 7 8 9 10 11 12 13 |
1) pwd 2) ls 3) exit #? 1 /home/ken/select-ex-dir #? 2 select-ex1.sh select-ex2.sh select-ex3.sh select-ex4.sh #? 4 あなたの入力した番号は4です #? 3 |
「$REPLY」が突然でてきたがこれはselectを使用するときに内部で生成される特別な変数だ。この中には、あなたの入力した値が代入される。数字の他文字列も表示される。
caseで処理を分岐、および実際にコマンドを起動させて、終了したらプロンプトを再表示するようにしている。
選択時のプロンプトを変更する
プロンプト変数を変更するとプロンプトの表示が変更できる。
プロンプト変数には「PS1、PS2、PS3、PS4」の4つあるが、PS1は通常のプロンプト、PS2はコマンド入力が完了していないときのプロンプト、対話的な継続されるプロンプト表示、telnetなどのプロンプトだ。PS3はselectなどのプロンプト、PS4はbashのデバックのためのプロンプトとなっている。
今回はPS3を変更しプロンプトを変えてみよう。
select-ex3.sh
1 2 3 4 5 6 7 8 9 10 11 12 13 |
#!/usr/bin/bash #プロンプトの変更 PS3="select item: " select VAR in pwd ls exit do #繰り返しの中でcase分を使用している。 case $VAR in "ls" ) ls -1 ;; "pwd" ) pwd ;; "exit" ) break ;; * ) echo "あなたの入力した番号は$REPLYです" esac done |
実行結果
$ ./select-ex3.sh
1 2 3 4 5 6 7 8 9 10 11 12 13 |
1) pwd 2) ls 3) exit select item: 1 /home/ken/select-ex-dir select item: 2 select-ex1.sh select-ex2.sh select-ex3.sh select-ex4.sh select item: 4 あなたの入力した番号は4です select item: 3 |
caseとwhileでメニュー表示と分岐
大体ではあるが以下のようにするとメニュー表示と分岐ができる。bashではなくshしか使えない環境などは無限ループと分岐処理を使用すれば、同じ様な処理が可能だ。
もっとつくりこめば、実際のselectと同じような動作をする実装が可能だが、非常に大がかりになってしまう。
vi select-ex4.sh
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 |
#!/usr/bin/bash echo "1 ) item1" echo "2 ) item2" echo "3 ) item3" echo "4 ) item4" while : do read -p: VAR case "$VAR" in 1 ) echo "あなたが選んだ項目は$VARです。" ;; 2 ) echo "あなたが選んだ項目は$VARです。" ;; 3 ) echo "あなたが選んだ項目は$VARです。" ;; 4 ) echo "あなたが選んだ項目は$VARです。" ;; * ) break ;; esac done |
実行結果
$ ./select-ex4.sh
1 2 3 4 5 6 7 8 9 10 11 12 13 |
1 ) item1 2 ) item2 3 ) item3 4 ) item4 :1 あなたが選んだ項目は1です。 :2 あなたが選んだ項目は2です。 :3 あなたが選んだ項目は3です。 :4 あなたが選んだ項目は4です。 :5 |
まとめ
このページではシェルスクリプトのselectについて、4つのサンプルコードを使ってご紹介した。selectについて一通り理解できただろうか?
selectは知っておくと便利な構文だ。ぜひ実際にサンプルを手元で組んで、実行をしてみていただきたい。