【Bash Shell Script】強大的命令提示字元?
Bash是Unix shell的一種,一般來說Bash就是可以接受用戶輸入命令的程式,包括Linux與MacOSX都將它作為預設shell,它有點類似Windows的命令提示字元,但是功能比較強大,比較像是Windows PowerShell。說了這麼多,為什麼要學bash呢?使用GUI來做事就好了呀?因為有些日常的鎖碎小事,可以利用系統內建的bash就可以處理了,比方說影音轉檔,就可以使用ffmpeg指令,加上迴圈就可以了,其實很多影音轉檔的GUI裡面都是包ffmpeg的。說了這麼多,我們就來慢慢瞭解bash的強大,學習一點簡單的Script吧。
Bash初體驗
建立一個Shell檔
- 當然只要是『純文字』型的編譯器都可以用來編譯,我這裡就使用VSCode來新建一個.sh檔方便說明,在這裡比較要注意的是檔案的『權限問題』,要使用chmod指令去讓.sh變成有可執行的權限,變更之後,可以看到該檔案的顏色變成『紅色字』,這就表示它可以執行。這點就跟Windons有很大的不同,不是副檔名是『.exe』就是可執行檔,在Linux的世界中,只要該檔案有可執行的『權限』就可以執行,文字檔也可以執行喲,只是…執行不會成功而已…T.T。
#! /bin/bash
echo "hello world"
bash hello.sh
./hello.sh
chmod +x hello.sh
./hello.sh
Bash參數
- Bash的參數是由『空白』去做為分隔,空白的數量沒有限制,只要是一個空白以上就可以了。
echo "我是一個 參數"
echo 參數1 參數2 參數3
變數
- 設定。
touch "bash is shell.mp3"
file="bash is shell.mp3"
rm $file
rm "$file"
變數擴展
- 利用大括弧可以讓變數更有可應用性 ($變數)
User="USER"
echo "$User, $Users, ${User}s"
特殊變數
- 介紹一些常用的特殊變數
echo "\$0 = $0"
echo "\$1 = $1"
echo "\$2 = $2"
echo "\$# = $#"
echo "\$* = $*"
echo "\$@ = $@"
echo "\$? = $?"
echo "\$$ = $$"
echo "\$! = $!"
echo "\$_ = $_"
數學運算
- 利用『(())』去做數學運算
i=5
echo $i
((i=i*5))
echo $i
利用指令結果當參數
- 利用『``/ $()』取得指令的結果
now=`date`
echo $now
time=$(date)
echo $time
Test運算
基本的Test運算
- Test運算就是指『[…]』,其中要注意的是要加入『空白』,有空白的分隔才會被當成運算使用
[ 1 = 1 ]; echo $?
[ 1 = 2 ]; echo $?
字串判斷
yourname='Kevin Chang' myname='William Weng'
[ $yourname = $myname ]; echo $?
[ "$yourname" = "$myname" ]; echo $?
[ "Kevin Chang" = "William Weng" ]; echo $?
Glob Pattern
- 其實就是正規式
echo *
echo *.sh
echo [h]*.sh
if判斷式
if
- 其實實際上在bash內它只是一行字,所以要注意『空格 / 分號』 (-gt: 大於)
if [ 2 -gt 1 ];
then echo "true";
fi
if [ 2 -gt 1 ]; then echo "true"; fi
if else
if [ 10 -gt 100 ];
then echo "true";
else echo "false";
fi
if elif else
if [ 1 = 2 ]; then
echo "true";
elif [ 1 = 3 ]; then
echo "false";
else
echo "1 != 2, 1 != 3"
fi
實際範例
if [ -e hello.sh ]; then
echo "hello.sh 存在";
else
echo "hello.sh 不存在";
fi
邏輯運算
- 『&& / -a』都叫做and,『!』叫not
if [ 1 = 1 ] && [ ! 1 = 2 ]; then
echo "true";
else
echo "false";
fi
if [ 1 = 1 -a 2 = 2 ]; then
echo "true";
else
echo "false";
fi
四則運算
- 利用bash做數字的運算
if [ ! $# -eq 3 ]; then
echo "參數數量不是三個";
exit;
fi
if [ $2 = "+" ]; then
echo "相加 = $(($1+$3))";
elif [ $2 = "-" ]; then
echo "相減 = $(($1-$3))";
else
echo "不知道耶"
fi
while迴圈
利用while跑迴圈
(( index=10 ));
while (( index > 0 )); do
echo "index = $index";
(( index-- ));
done
利用while讀取csv檔
while read line; do # 一次讀取一行文字
IFS=','; # 設定分隔號為,
read -a records <<< "$line"; # 將line內容存入records中
echo "${records[0]}, ${records[1]}, ${records[2]}"
done < $1 # 將檔名(參數1)當成輸入資料
for迴圈
利用for跑迴圈
for index in {10..1}; do
echo $index;
done
datas="A B C D E";
for string in $datas; do
echo $string;
done
讀取參數
- 裡面會用到一些Bash的特殊符號
for paramater in $*; do # $* => 傳回的是String
echo $paramater;
done
for paramater in $@; do # $@ => 傳回的是Array
echo $paramater;
done
讀取檔案名稱
for filename in *.sh; do
echo $filename;
done
讀取檔案內容
- 這裡有一些文字處理的相關內容
IFS="\n"
for line in (cat $1); do
echo $line;
done
switch迴圈
字串比較
- switch比較要注意的是『)跟;;』的語法
case "$1" in
william)
echo "Hello $1";;
jack)
echo "Good morning, $1";;
*)
echo "How are you, $1";;
esac
數字比較
- 話說bash的結尾字好像都是『倒著寫』耶?
case "$1" in
0)
echo "Zero";;
1)
echo "First";;
*)
echo "Other";;
esac
select迴圈
字串比較
- 內有bash的內建變數
select filename in *; do
echo "You select $filename, $REPLY";
break;
done
select + switch
colors="red green blue"
select color in $colors; do
case $color in
"$quit")
echo "bye"
break;;
*)
echo "selected color is $color";;
esac
done
function
基本語法
- 使用function關鍵字或()
function my_print {
echo "@my_print";
}
your_print () {
echo "@your_print";
}
my_print;
your_print;
一般函式
hello () {
echo -e "hello, \$1 = $1, \$2 = $2";
}
isEqual () {
if [ $1 -eq $2 ]; then
return 0;
fi
return 1;
}
hello william go
isEqual 1 2
echo $?
離開執行
exit_func () {
if [ $1 = 1 ]; then
echo "exit in func";
exit 1;
fi
}
exit_func $1;
echo "exit in main";
exit 0;
範例程式碼下載
後記
- 因為個人常常錄製mov,學了一點簡單的bash之後,也不用使用IDE去轉檔,轉成mp4就這麼簡單,三行就OK…這篇只是我的個人筆記而已,學海無涯,各位一起努力吧,加油…
#!/bin/bash
for name in *.mov; do
ffmpeg -i "$name" -an "${name%.*}.mp4"
done
# Windows的可以喲
for /F "delims=" %i in ('dir /b *.mov') do ffmpeg -i "%i" "%~ni.mp4"