一、Shell介紹
Shell是linux系統中相當強悍的軟件,他類似於windwos下的cmd.exe.在linux下,shell作爲命令語言,它交互式解釋和執行用戶輸入的命令或者自動地解釋和執行預先設定好的一連串的命令;作爲程序設計語言,它定義了各種變量和參數,並提供了許多在高級語言中才具有的結構控制,包括循環和分支。
二、初識shell腳本
Linux系統下的shell默認爲bash,所以在寫腳本的時候首行一定要是#!/bin/bash,這一行用於聲明使用/bin/bash作爲腳本語言。
腳本文件中,所有以#開頭的行均爲註釋行,不會被執行。
這是一個腳本,實現功能的很簡單,顯示This is a test shell
vim shell.sh
#!/bin/bash # Discribe:This is a test shell. # Version 0.0.1 # Author:Myb # DATE 2014-3-24 echo " This is a test shell."
:wq保存退出
bash –n shell.sh檢查腳本的語法錯誤,不執行腳本。如果沒有錯誤,則不會顯示任何信息。
在linux下沒有返回信息很多時候都會是最好的消息。
chmod +x shell.sh 賦予shell.sh執行權
./shell.sh 或者 /bin/bash shell.sh執行腳本
[root@myb362 ~]# bash -n shell.sh [root@myb362 ~]# chmod +x shell.sh [root@myb362 ~]# ./shell.sh This is a test shell. [root@myb362 ~]#
這就是一個非常簡單的腳本。當然我們也可以稍微填充一下剛纔的腳本。
比如,添加一個用戶名user1,密碼與用戶名相同。
如果不使用腳本的話,這也是一個非常簡單的操作。
[root@myb362 ~]# useradd user1 [root@myb362 ~]# echo user1 | passwd --stdin user1 Changing password for user user1. passwd: all authentication tokens updated successfully. [root@myb362 ~]#
這樣就添加了一個用戶user1,,並且密碼與用戶名相同。
寫入腳本中,就會是這樣的
#!/bin/bash # Discribe:This is a test shell. # Version 0.0.1 # Author:Myb # DATE 2014-3-24 echo " This is a test shell for add user user2." useradd user2 echo user2 | passwd --stdin user2
:wq保存退出,執行./shell.sh,查看passwd文件看出user2已經添加成功。
[root@myb362 ~]# ./shell.sh This is a test shell for add user user2. Changing password for user user2. passwd: all authentication tokens updated successfully. [root@myb362 ~]# cat /etc/passwd | grep "^user2" user2:x:6007:6007::/home/user2:/bin/bash
簡單來講,shell腳本就是很多命令的堆積,比如,我們需要添加user1到user10這10個用戶,那麼我們完全可以在上邊的腳本中將兩行命令複製10次,從user1一直添加到user10.雖然這種方式可以完成我們的要求,但是非常的繁瑣,如果是添加100或者1000個用戶呢?那可能就要瘋了。
那針對這種循環執行的命令,shell腳本中,可以使用for、while和until來控制循環語句。
for循環
事先提供一個元素列表,而後,使用變量去遍歷此元素列表,每訪問一個元素,就執行一次循環體,直到元素訪問完畢。
用法格式:
for VAR_NAME in 元素1 元素2 …;do 語句1; 語句2; … done
那添加3個用戶user3、user4、user5就可以使用for循環語句來實現添加
useradd.sh腳本
#!/bin/bash # # for i in user3 user4 user5;do #for循環控制遍歷列表爲user3 user4 user5 將遍歷列表中的值傳參給i useradd $i #添加用戶$i,$i 從遍歷列表中逐個取出 echo $i | passwd --stdin $i #給用戶賦予密碼 --stdin將echo中的值傳參給passwd命令 done
:wq保存退出
sh –n useradd.sh 檢查語法錯誤,賦予執行權限 chmod +x useradd.sh 並執行 ./useradd.sh
[root@myb362 ~]# sh -n useradd.sh [root@myb362 ~]# chmod +x useradd.sh [root@myb362 ~]# ./useradd.sh Changing password for user user3. passwd: all authentication tokens updated successfully. Changing password for user user4. passwd: all authentication tokens updated successfully. Changing password for user user5. passwd: all authentication tokens updated successfully. [root@myb362 ~]# grep "^user" /etc/passwd user2:x:6007:6007::/home/user2:/bin/bash user3:x:6008:6008::/home/user3:/bin/bash user4:x:6009:6009::/home/user4:/bin/bash user5:x:6010:6010::/home/user5:/bin/bash [root@myb362 ~]#
用戶user3,user4,user5 添加成功
這樣可以大大的減少我們需要輸入的命令,其實這個腳本還有一個地方是可以進行優化的,因爲我們的遍歷列表中user3、user4、user5只有最後一位數字變化,那麼我們爲了減少輸入字符的長度,還可以這樣寫。
#!/bin/bash # for i in 3 4 5;do useradd user$i echo user$i | passwd –-stdin user$i done
這樣也是可以執行成功的,前提是你需要刪除你的user3、4、5用戶
userdel –r user3
userdel –r user4
userdel –r user5
使用for循環語句可以高效的完成工作,但是這種列表方式有時也會給我們的工作帶來很多麻煩,比如需要添加100個用戶,將100個用戶寫入列表中,實在是太麻煩了。
列表的生成方式:
1、逐個給出,如:user1 user2 user3
2、使用通配符實現文件通配,如:for File in /var/*
3、使用命令生成列表,如:for File in `ls /var`
4、生成數字序列
{}:{起始數字..結束數字},例如{1..100}表示從1到100
`seq [起始數字] [步長] 結束數字`
例如:`seq 1 2 100` 從1開始,步長爲2,到100結束
結果: 1 3 5 7 9 …
如何使用通配符實現文件通配:
常用的列表生成方式,比如我想要查看/var目錄下的所有文件類型
使用for語句查看
[root@myb362 ~]# vi filetype.sh #!/bin/bash # # for File in /var/*;do file $File done
添加執行權限 chmod +x filetype.sh ./filetype.sh查看文件類型
[root@myb362 ~]# ./filetype.sh /var/cache: directory /var/cvs: directory /var/db: directory /var/empty: directory /var/games: directory /var/lib: directory /var/local: directory /var/lock: directory /var/log: directory /var/mail: symbolic link to `spool/mail' /var/nis: directory /var/opt: directory /var/preserve: directory /var/run: directory /var/spool: directory /var/tmp: sticky directory /var/yp: directory
使用命令生成列表
還以上一個示例來說,這次使用命令生成列表的方式完成
#!/bin/bash for File in `ls /var/` ;do # ls /var/ 列出var目錄下的所有文件當遍歷列表 file /var/$File #這裏別忘記了在$File前面加上文件的目錄/var/ done
顯示結果一樣
[root@myb362 ~]# ./filetype2.sh /var/cache: directory /var/cvs: directory /var/db: directory /var/empty: directory /var/games: directory /var/lib: directory /var/local: directory /var/lock: directory /var/log: directory /var/mail: symbolic link to `spool/mail' /var/nis: directory /var/opt: directory /var/preserve: directory /var/run: directory /var/spool: directory /var/tmp: sticky directory /var/yp: directory
生成數字列表
太好用的列表生成方式了
比如:使用for循環添加10個用戶,用戶名從user11-20,並添加密碼,密碼同用戶名。
[root@myb362 ~]# vi useradd2.sh #!/bin/bash # # for User in `seq 11 20`;do useradd user$User echo user$User | passwd --stdin user$User done
:wq保存退出
chmod +x 添加執行權限 ./useradd2.sh執行腳本
[root@myb362 ~]# chmod +x useradd2.sh [root@myb362 ~]# ./useradd2.sh Changing password for user user11. passwd: all authentication tokens updated successfully. Changing password for user user12. passwd: all authentication tokens updated successfully. Changing password for user user13. passwd: all authentication tokens updated successfully. Changing password for user user14. passwd: all authentication tokens updated successfully. Changing password for user user15. passwd: all authentication tokens updated successfully. Changing password for user user16. passwd: all authentication tokens updated successfully. Changing password for user user17. passwd: all authentication tokens updated successfully. Changing password for user user18. passwd: all authentication tokens updated successfully. Changing password for user user19. passwd: all authentication tokens updated successfully. Changing password for user user20. passwd: all authentication tokens updated successfully. [root@myb362 ~]# cat /etc/passwd | grep "^user" user2:x:6007:6007::/home/user2:/bin/bash user3:x:6008:6008::/home/user3:/bin/bash user4:x:6009:6009::/home/user4:/bin/bash user5:x:6010:6010::/home/user5:/bin/bash user11:x:6011:6011::/home/user11:/bin/bash user12:x:6012:6012::/home/user12:/bin/bash user13:x:6013:6013::/home/user13:/bin/bash user14:x:6014:6014::/home/user14:/bin/bash user15:x:6015:6015::/home/user15:/bin/bash user16:x:6016:6016::/home/user16:/bin/bash user17:x:6017:6017::/home/user17:/bin/bash user18:x:6018:6018::/home/user18:/bin/bash user19:x:6019:6019::/home/user19:/bin/bash user20:x:6020:6020::/home/user20:/bin/bash
添加成功。
由於輸出信息很多,我們不想讓信息輸出到屏幕上,就可以在命令後添加&>/dev/null,信息就不會輸出到屏幕上。
如下
[root@myb362 ~]# vi useradd2.sh #!/bin/bash # # for User in `seq 11 20`;do useradd user$User &>/dev/null echo user$User | passwd --stdin user$User &>/dev/null done
這樣無論錯誤輸出和標準輸出都不會輸出到屏幕上了。如有疑問,請自行google標準輸入、標準輸出、錯誤輸出、輸入重定向和輸出重定向
看到這裏,是不是想起了一個非常經典的題目,從1加到100,計算總和。
首先,我們要知道怎麼在shell腳本中進行算術運算。
1、shell不支持浮點數、計算結果中的浮點數會被圓整爲整數:1.23=1 1.99=1
2、shell運算符
+(加)
-(減)
*(乘)
/(除)
%(取餘)
3、算術運算的實現方式:假如 A=5,B=9
$[expression]: 例如:$[$A+$B]
$((expression)):例如:$(($A+$B))
let expression:例如:let E=$A+$B
expr expression:例如:F=`expr $A + $B`
一般在腳本中比較常用的是第一種和第三種方式。
好了,寫一個腳本計算1加到100的值
#/bin/bash # # Sum=0 # 定義一個變量等於0 for i in {1..100};do #定義列表範圍從1-100 Sum=$[$Sum+$i] # done echo “Sum is $Sum”
保存退出,賦予執行權限,執行腳本。結果如下
[root@myb362 ~]# ./sum.sh Sum is 5050 [root@myb362 ~]#
Sum=$[$Sum+$i] 解釋:
第一次循環時,$Sum=0 $i=1 $[$Sum+$i]=1 然後將1重新賦值給Sum,
第二次循環時,$Sum=1 $i=2 $[$Sum+$i]=3 然後將3重新賦值給Sum,
第三次循環時,$Sum=3 $i=3 $[$Sum+$i]=6 然後將6重新賦值給Sum,
……
直至循環體結束。
那求100以內所有奇數的和、偶數的和也是使用這種方法。
[root@myb362 ~]# vi sum2.sh #!/bin/bash # # EvenSum=0 OddSum=0 for i in `seq 1 2 100`;do #列表爲1 3 5 7 9 … OddSum=$[$OddSum+$i] done for i in `seq 2 2 100`;do EvenSum=$[$EvenSum+$i] #列表爲2 4 6 8 10 … done echo "OddSum:$OddSum" echo "EvenSum:$EvenSum"
賦予權限,執行。結果如下:
[root@myb362 ~]# chmod +x sum2.sh [root@myb362 ~]# ./sum2.sh OddSum:2500 EvenSum:2550
這是使用for循環語句來實現1到100之間的奇偶數之和的方法,以後我們還會學到很多簡單的方法。
結束:
for循環體在shell編程中非常的好用,他可以使我們快速便捷的完成一些需要重複操作的工作。當然還有while和until這種循環體,後邊會專門寫。感謝各位的圍觀,希望能夠幫助需要的人,如果有錯誤的地方,希望大家能夠指出,不勝感激。