Shell編程快速入門指南

第一個shell腳本

#!/bin/bash
echo "hello, world"

運行程序能夠做爲解釋器參數或者做爲可執行程序shell

bash test.sh
chmod +x test.sh
test.sh

變量

命名數組

name="huruji"

須要注意的是變量名與等號之間不能有空格。bash

使用

echo $name
echo ${name}

使用在變量名前添加$便可,{}表示這個變量名的邊界。函數

只讀變量工具

name="huruji"
readonly name

使用readonly能夠將變量定義爲只讀變量,只讀變量不能再次賦值測試

刪除變量spa

name="huruji"
unset name

使用unset刪除變量,以後不能再使用。code

字符串

name="huruji"

echo "my name is $name"

字符串可使用單引號和雙引號,單引號中不能包含單引號,即便轉義單引號也不次那個,雙引號則能夠,雙引號也可使用字符串。orm

拼接blog

name="huruji"
hello="my name is ${name}"

獲取字符串長度

str="huruji"
echo ${#str} #6

提取子字符串

str="huruji"
echo ${str:2:3}

從字符串的第二個字符開始提取3個字符,輸出ruj

查找

str="huruji"
echo `expr index "$str" u`

此時輸出2,由於此時第一個字符位置從1開始

數組

定義

names=("huruji" "greywind" "xie")
echo ${names[0]}
echo ${names[2]}

讀取

echo ${names[2]}
echo ${names[@]}

如上例子,使用@能夠獲取數組中的全部元素

獲取長度

length=${#names[@]}
length=${#names[*]}

Shell參數傳遞

執行Shell腳本的時候,能夠向腳本傳遞參數,在Shell中獲取這些參數的格式爲$n,即$1,$2.......,

echo "第一個參數是:$1"
echo "第一個參數是:$2"
echo "第一個參數是:$3"

運行

chmod +x test.sh
test.sh 12 13 14

則此時輸出:

第一個參數是:12
第一個參數是:13
第一個參數是:14

此外,還有其餘幾個特殊字符來處理參數

  • $#:傳遞腳本的參數個數
  • $*:顯示全部的參數
  • $$:腳本當前運行的進程ID號
  • $!:後臺運行的最後一個進程的ID號
  • $@:返回全部參數
  • $-:顯示Shell的使用的當前選項
  • $?:退出的狀態,0表示沒有錯誤,其餘則表示有錯誤

運算

算數運算
原生bash不支持簡單的數學運算,能夠藉助於其餘命令來完成,例如awk和expr,其中expr最經常使用。expr是一款表達式計算工具,使用它能完成表達式的求值操做。

val=`expr 2 + 2`
echo $val

須要注意的是運算符兩邊須要空格,且使用的是反引號。
算術運算符包括:+ - × / % = == !=

關係運算
關係運算只支持數字,不支持字符串,除非字符串的值是數字。

a=12
b=13
if [ $a -eq $b ]
    then
    echo "相等"
else
    echo "不等"
fi
  • -eq:是否相等
  • -ne:是否不等
  • -gt:大於
  • -lt:小於
  • -ge:大於等於
  • -le:小於等於

布爾運算

  • !:非
  • -o:或
  • -a:與

邏輯運算符

  • &&:邏輯與
  • ||:邏輯或

字符串運算符

  • =:相等 [ $a = $b ]
  • !=:不等 [ $a != $b ]
  • -z:字符串長度是否爲0,爲0返回true [ -z $a ]
  • -n:字符串長度是否爲0,不爲0返回true [ -n $a ]
  • str:字符串是否爲空,不爲空返回true [ $a ]

文件測試運算符
用於檢測Unix文件的各類屬性。

  • -b:檢測文件是否爲塊設備文件 [ -b $file ]
  • -c:檢測文件是否爲字符設備文件 [ -c $file ]
  • -d:檢測文件是否爲目錄 [ -d $file ]
  • -f:檢測文件是否爲普通文件 [ -f $file ]
  • -g:檢測文件是否設置了SGID位 [ -g $file ]
  • -k:檢測文件是否設置了粘着位 [ -k $file ]
  • -p:檢測文件是不是有名管道 [ -p $file ]
  • -u:檢測文件是否設置了SUID位 [ -u $file ]
  • -r:檢測文件是否可讀 [ -r $file ]
  • -w:檢測文件是否可寫 [ -w $file ]
  • -x:檢測文件是否可執行 [ -x $file ]
  • -s:檢測文件大小是否大於0 [ -s $file ]
  • -e:檢測文件是否存在 [ -e $file ]
file="/home/greywind/Desktop/learnShell/test.sh"

if [ -e $file ]
    then
    echo "文件存在"
else
    echo "文件不存在"
fi

if [ -r $file ]
    then
    echo "可讀"
else
    echo "不可讀"
fi

if [ -w $file ]
    then
    echo "可寫"
else
    echo "不可寫"
fi


if [ -x $file ]
    then
    echo "可執行"
else
    echo "不可執行"
fi

if [ -d $file ]
    then
    echo "是目錄"
else
    echo "不是目錄"
fi

if [ -f $file ]
    then
    echo "是普通文件"
else
    echo "不是普通文件"
fi

echo

echo在顯示輸出的時候能夠省略雙引號,使用read命令能夠從標準輸入中讀取一行並賦值給變量

read name
echo your name is $name

換行使用轉義n,不換行使用c
此外使用 > 能夠將echo結果寫入指定文件,這個文件不存在會自動建立

echo "it is a test" > "/home/greywind/Desktop/learnShell/hello"

使用反引號能夠顯示命令執行的結果,如date、history、pwd

echo `pwd`
echo `date`

printf

Shell中的輸出命令printf相似於C語言中的printf(),
語法格式:

printf format-string [arguments...]
printf "%-10s %-8s %-4s\n" 姓名 性別 體重kg  
printf "%-10s %-8s %-4.2f\n" 郭靖 男 66.1234 
printf "%-10s %-8s %-4.2f\n" 楊過 男 48.6543 
printf "%-10s %-8s %-4.2f\n" 郭芙 女 47.9876

test

test命令用於檢查某個條件是否成立,能夠進行數值、字符、文件三方面的測試

a=100
b=200
if test a == b
    then
    echo "相等"
else
    echo "不等"
fi

流程控制

if

a=100
b=200
if test $a -eq $b
    then
    echo "相等"
else
    echo "不等"
fi
a=100
b=200
if test $a -eq $b
    then
    echo "相等"
elif test $a -gt $b
    then
    echo "a大於b"
elif test $a -lt $b
    then
    echo "a小於b"
fi

for

for num in 1 2 3 4
do
    echo ${num}
done
num=10
for((i=1;i<10;i++));
do
    ((num=num+10))
done
echo $num

while

num=1
while [ $num -lt 100 ]
do
    ((num++))
done

echo $num

無限循環

while:
do
      command
done
while true
do
      command
done
for (( ; ; ))

until

until condition
do
      command
done

case

case 值 in
模式1)
    command1
    command2
    ...
    commandN
    ;;
模式2)
    command1
    command2
    ...
    commandN
    ;;
esac

須要注意的是與其餘語言不一樣Shell使用;;表示break,另外沒有一個匹配則使用*捕獲該值

echo "輸入1 2 3任意一個數字"
read num
case $num in
    1)echo "輸入了1"
;;
    2)echo "輸入了2"
;;
    3)echo "輸入了3"
;;
    *)echo "輸入的值不是1 2 3"
;;
esac

與其餘語言相似,循環可使用break和continue跳出

函數

函數定義
用戶自定義函數可使用或者不使用function關鍵字,同時指定了return值則返回這個值,若是沒有return語句則以最後一條運行結果做爲返回值。

function first(){
    echo "hello world"
}
first(){
    echo "hello world"
}

調用函數直接使用這個函數名便可

first

函數參數
調用函數能夠傳入參數,函數內部使用$n獲取傳入的參數,相似於運行程序使用時獲取使用的參數,不過須要注意的是兩位數以上應該使用{}告訴shell邊界例如${12}、${20}

function add(){
    num=0;
    for((i=1;i<=$#;i++));
    do
        num=`expr $i + $num`
    done
    return $num
}
add 1 2 3 4 5
a=$?

echo $a

函數自己是一個命令,因此只能經過$?來得到這個返回值

輸入輸出重定向

在上文的例子中可使用 > 能夠將echo結果寫入指定文件,這就是一種輸出重定向,重定向主要有如下:

  • command > file:輸出重定向至文件file
  • command < file:輸入重定向至文件file
  • command >> file:輸出以追加的方式重定向至文件file
  • n > file:將文件描述符爲n的文件重定向至文件file
  • n >> file:將文件描述符爲 n 的文件以追加的方式重定向到文件file
  • n >& m:將輸出文件 m 和 n 合併
  • n <& m:將輸入文件 m 和 n 合併
  • << tag:將開始標記 tag 和結束標記 tag 之間的內容做爲輸入

將whoami命令輸出保存到user文件中

who > "./user"

使用cat命令就能夠看到內容已經保存了,若是不想覆蓋文件的內容那麼就使用追加的方式便可。

who >> "./user"

Shell文件包含

Shell腳本能夠包含外部腳本,能夠很方便的封裝一些公用的代碼做爲一個獨立的文件,包含的語法格式以下:

. filename
# 或
source filename

如:
test1.sh

echo "hello world"

test.sh

source ./test1.sh

echo "hello"
相關文章
相關標籤/搜索