)
一 ~ 四章【點擊此處查看】五、shell 編程5.1、shell 概述5.1.1 shell 是什么Shell是一個命令行解釋器它為用戶提供了一個向Linux內(nèi)核發(fā)送請求以便運行程序的界面系統(tǒng)級程序用戶可以用Shell來啟動、掛起、停止甚至是編寫一些程序。Shell還是一個功能相當強大的編程語言易編寫易調(diào)試靈活性較強。Shell是解釋執(zhí)行的腳本語言在Shell中可以直接調(diào)用Linux系統(tǒng)命令。5.1.2 shell 的分類Bourne Shell從1979起Unix就開始使用Bourne ShellBourne Shell的主文件名為sh。C Shell C Shell主要在BSD版的Unix系統(tǒng)中使用其語法和C語言相類似而得名Shell的兩種主要語法類型有Bourne和C這兩種語法彼此不兼容。Bourne家族主要包括sh、ksh、Bash、psh、zshC家族主要包括csh、tcshBash Bash與sh兼容現(xiàn)在使用的Linux 就是使用Bash作為用戶的基本Shell。5.2、shell 腳本的執(zhí)行方式5.2.1 echo 輸出命令命令名稱echoecho[選項][輸出內(nèi)容]選項-e 支持反斜線控制的字符轉(zhuǎn)換控制字符作用\輸出\\a輸出警告音\b退格鍵向左刪除鍵\c取消輸出行末的換行符和“-n”選項一致\eESCAPE鍵\f換頁符\n換行符\r回車鍵\t制表符Tab鍵\v直制表符\0nnn按照八進制ASCII碼表輸出字符0為數(shù)字零nnn為三位八進制數(shù)\xhh按照十六進制ASCII碼表輸出字符其中hh是兩位十六進制數(shù)示例[rootzhangRabbitMQ zhang]# echo -e ab\bcac[rootzhangRabbitMQ zhang]# echo -e a\tb\tc\nd\te\tfa b c d e f5.2.2 編寫腳本[rootzhangRabbitMQ zhang]# vi /tmp/hello.sh#/bin/bashechohelloword5.2.3 執(zhí)行腳本[rootzhangRabbitMQ zhang]# chmod 755 /tmp/hello.sh[rootzhangRabbitMQ zhang]# /tmp/hello.shhelloword5.3、Bash的基本功能5.3.1 歷史命令與命令補全歷史命令history命令名稱history[rootlocalhost ~]# history [選項] [歷史命令保存文件]選項-c 清空歷史命令-w 把緩存中的歷史命令寫入歷史命令保存文件 ~/.bash_history歷史命令默認會保存1000條,可以在環(huán)境變量配置文件/etc/profile中進行修改歷史命令的調(diào)用使用上、下箭頭調(diào)用以前的歷史命令使用“!n”重復執(zhí)行第n條歷史命令使用“!!”重復執(zhí)行上一條命令使用“!字串”重復執(zhí)行最后一條以該字串開頭的命令命令與文件補全在Bash中命令與文件補全是非常方便與常用的功能我們只要在輸入命令或文件時按“Tab”鍵就會自動進行補全5.3.2 命名別名與常用快捷鍵命令別名[rootlocalhost ~]# alias 別名原命令#設定命令別名[rootlocalhost ~]# alias#查詢命令別名命令的執(zhí)行順序第一順位執(zhí)行用絕對路徑或相對路徑執(zhí)行的命令。第二順位執(zhí)行別名。第三順位執(zhí)行Bash的內(nèi)部命令。第四順位執(zhí)行按照$PATH環(huán)境變量定義的目錄查找順序找到的第一個命令。讓別名永久生效需要把配置寫入配置文件/root/.bashrc中Bash 常用快捷鍵5.3.3 輸入輸出重定向同時輸出正確和錯誤5.3.4 多命令執(zhí)行與管道符多命令順序執(zhí)行管道符|命令名稱|# 語法將命令1的輸出結(jié)果作為命令2的輸入 命令1 | 命令2命令格式[rootlocalhost ~]# 命令1 | 命令2#命令1的正確輸出作為命令2的操作對象例子[rootlocalhost ~]# ll -a /etc/ | more[rootlocalhost ~]# netstat -an | grep ESTABLISHED查找aries用戶cat/etc/passwd|grep-n “baizhi” 查找aries組cat/etc/group|grep-n “baizhi” 查找sshd進程ps-aux|grep sshd5.3.5 通配符與其他特殊符號通配符其他特殊符號5.4、Bash 變量5.4.1 用戶自定義變量什么是變量變量是計算機內(nèi)存的單元其中存放的值可以改變。當Shell腳本需要保存一些信息時如一個文件名或是一個數(shù)字就把它存放在一個變量中。每個變量有一個名字所以很容易引用它。使用變量可以保存有用信息使系統(tǒng)獲知用戶相關設置變量也可以用于保存暫時信息。變量設置規(guī)則變量名稱可以由字母、數(shù)字和下劃線組成但是不能以數(shù)字開頭。如果變量名是“2name”則是錯誤的。在Bash中變量的默認類型都是字符串型如果要進行數(shù)值運算則必修指定變量類型為數(shù)值型。變量用等號連接值等號左右兩側(cè)不能有空格。變量的值如果有空格需要使用單引號或雙引號包括。在變量的值中可以使用“\”轉(zhuǎn)義符。如果需要增加變量的值那么可以進行變量值的疊加。不過變量需要用雙引號包含“變量名”或用 變量名”或用變量名”或用{變量名}包含。如果是把命令的結(jié)果作為變量值賦予變量則需要使用反引號或$()包含命令。環(huán)境變量名建議大寫便于區(qū)分。變量分類用戶自定義變量 ? 環(huán)境變量這種變量中主要保存的是和系統(tǒng)操作環(huán)境相關的數(shù)據(jù)。位置參數(shù)變量這種變量主要是用來向腳本當中傳遞參數(shù)或數(shù)據(jù)的變量名不能自定義變量作用是固定的。預定義變量是Bash中已經(jīng)定義好的變量變量名不能自定義變量作用也是固定的。本地變量變量定義[rootlocalhost ~]# nameshen chao變量疊加[rootlocalhost ~]# aa123[rootlocalhost ~]# aa$aa456[rootlocalhost ~]# aa${aa}789變量調(diào)用[rootlocalhost ~]# echo $name變量查看[rootlocalhost ~]# set查看當前系統(tǒng)全部變量變量刪除[rootlocalhost ~]# unset name5.4.2 環(huán)境變量環(huán)境變量是什么用戶自定義變量只在當前的Shell中生效而環(huán)境變量會在當前Shell和這個Shell的所有子Shell當中生效。如果把環(huán)境變量寫入相應的配置文件那么這個環(huán)境變量就會在所有的Shell中生效設置環(huán)境變量export變量名變量值 申明變量env查詢變量unset變量名 刪除變量系統(tǒng)常見環(huán)境變量PATH系統(tǒng)查找命令的路徑[rootlocalhost ~]# echo $PATH /usr/lib/qt-3.3/bin:/usr/local/sbin:/usr/local/bin: /sbin:/bin:/usr/sbin:/usr/bin:/root/binPATH$PATH:/root/sh PATH變量疊加 PS1定義系統(tǒng)提示符的變量 \d顯示日期格式為“星期 月 日” \h顯示簡寫主機名。如默認主機名“l(fā)ocalhost” \t顯示24小時制時間格式為“HH:MM:SS” \T顯示12小時制時間格式為“HH:MM:SS” \A顯示24小時制時間格式為“HH:MM” \u顯示當前用戶名 \w顯示當前所在目錄的完整名稱 \W顯示當前所在目錄的最后一個目錄 \#執(zhí)行的第幾個命令\$提示符。如果是root用戶會顯示提示符為“#”如果是普通用戶會顯示提示符為“$”示例[rootlocalhost ~]# PS1[\u\t \w]\$ [root04:50:08 /usr/local/src]#PS1[\u\ \h \# \W]\$‘[root04:53 上午 localhost 31 src]#PS1[\u\h \W]\$ 5.4.3 位置參數(shù)變量位置參數(shù)變量示例#!/bin/bashnum1$1num2$2sum$(($num1$num2))#變量sum的和是num1加num2echo$sum#打印變量sum的值[rootzhangRabbitMQ zhang]# /tmp/sum.sh 1 235.4.4 預定義變量5.5、Bash運算符5.5.1 數(shù)值運算與運算符declare聲明變量類型數(shù)值運算[rootlocalhost ~]# declare [/-][選項] 變量名選項- 給變量設定類型屬性: 取消變量的類型屬性-i: 將變量聲明為整數(shù)型integer-x: 將變量聲明為環(huán)境變量-p: 顯示指定變量的被聲明的類型 方法1[rootlocalhost ~]# aa11[rootlocalhost ~]# bb22 #給變量aa和bb賦值[rootlocalhost ~]# declare -i cc$aa$bb方法2expr或let數(shù)值運算工具[rootlocalhost ~]# aa11[rootlocalhost ~]# bb22#給變量aa和變量bb賦值[rootlocalhost ~]# dd$(expr $aa $bb)#dd的值是aa和bb的和。注意“”號左右兩側(cè)必須有空格方法3“$((運算式))”或“$[運算式]”(推薦)[rootlocalhost ~]# aa11[rootlocalhost ~]# bb22[rootlocalhost ~]# ff$(( $aa$bb ))[rootlocalhost ~]# gg$[ $aa$bb ]5.6、環(huán)境變量配置文件5.6.1 配置文件簡介source命令source命令通常用于保留、更改當前shell中的環(huán)境變量。[rootlocalhost ~]# source 配置文件或[rootlocalhost ~]# . 配置文件環(huán)境變量配置文件簡介環(huán)境變量配置文件中主要是定義對系統(tǒng)的操作環(huán)境生效的系統(tǒng)默認環(huán)境變量比如PATH、HISTSIZE、PS1、HOSTNAME等默認環(huán)境變量。/etc/profile/etc/profile.d/*.sh~/.bash_profile~/.bashrc/etc/bashrc5.6.2 環(huán)境變量配置文件作用配置文件列表如下/etc/profile/etc/profile.d/*.sh~/.bash_profile~/.bashrc/etc/bashrctips:/etc 目錄下的對所有用戶都生效~/.bash_profile 和 ~/.bashrc - 每個用戶自己的配置文件只對用戶生效。配置文件讀取順序上圖從左到右如果有疊加。后面的命令會覆蓋前面的命令。/etc/profile的作用USER變量LOGNAME變量MAIL變量PATH變量HOSTNAME變量HISTSIZE變量umask調(diào)用/etc/profile.d/*.sh文件~/.bash_profile的作用用了~/.bashrc文件。在PATH變量后面加入了“:$HOME/bin”這個目錄5.6.3 其他配置文件和登錄信息注銷時生效的環(huán)境變量配置文件~/.bash_logout其他配置文件~/bash_historyShell登錄信息本地終端歡迎信息 /etc/issue5.7、正則表達式5.7.1 正則表達式與通配符正則表達式用來在文件中匹配符合條件的字符串正則是包含匹配。grep、awk、sed等命令可以支持正則表達式。通配符用來匹配符合條件的文件名通配符是完全匹配。ls、find、cp這些命令不支持正則表達式所以只能使用shell自己的通配符來進行匹配了。基礎正則表達式示例1*前一個字符匹配0次或多次 ● grepa*test_rule.txt#匹配所有內(nèi)容包括空白行● grepaa*test_rule.txt#匹配至少包含有一個a的行● grepaaa*test_rule.txt#匹配最少包含兩個連續(xù)a的字符串● grepaaaaa*test_rule.txt#則會匹配最少包含四個個連續(xù)a的字符串示例2.匹配除了換行符外任意一個字符 ● greps..dtest_rule.txt#“s..d”會匹配在s和d這兩個字母之間一定有兩個字符的單詞● greps.*dtest_rule.txt#匹配在s和d字母之間有任意字符● grep.*test_rule.txt#匹配所有內(nèi)容0或多個任意字符示例3^匹配行首$匹配行尾 ● grep^Mtest_rule.txt#匹配以大寫“M”開頭的行● grepn$test_rule.txt#匹配以小寫“n”結(jié)尾的行● grep-n^$test_rule.txt#會匹配空白行示例4[]匹配中括號中指定的任意一個字符只匹配一個字符 ● greps[ao]idtest_rule.txt#匹配s和i字母中要不是a、要不是o● grep[0-9]test_rule.txt#匹配任意一個數(shù)字● grep^[a-z]test_rule.txt#匹配用小寫字母開頭的行示例5[^]匹配除中括號的字符以外的任意一個字符 ● grep^[a-z]test_rule.txt#匹配不用小寫字母開頭的行● grep^[a-zA-Z]test_rule.txt#匹配不用字母開頭的行 “\” 轉(zhuǎn)義符● grep\.$test_rule.txt#匹配使用“.”結(jié)尾的行示例6\{n\}表示其前面的字符恰好出現(xiàn)n次 ● grepa\{3\}test_rule.txt#匹配a字母連續(xù)出現(xiàn)三次的字符串● grep[0-9]\{3\}test_rule.txt#匹配包含連續(xù)的三個數(shù)字的字符串示例7\{n,\}表示其前面的字符出現(xiàn)不小于n次 ● grep^[0-9]\{3,\}[a-z]test_rule.txt#匹配最少用連續(xù)三個數(shù)字開頭的行示例8\{n,m\}匹配其前面的字符至少出現(xiàn)n次最多出現(xiàn)m次 ???????● grepsa\{1,3\}itest_rule.txt#匹配在字母s和字母i之間有最少一個a最多三個a5.8 字符串截取命令5.8.1 cut 字段提取命令[rootlocalhost ~]# cut [選項] 文件名選項-f列號 提取第幾列-d分隔符 按照指定分隔符分割列1.創(chuàng)建演示文件student.txt[rootlocalhost ~]# vi student.txtID Name gender Mark1Liming M862Sc M903Gao M83示例[rootlocalhost ~]# cut -f 2 student.txt#提取第二列[rootlocalhost ~]# cut -f 2,3 student.txt#提取第二第三列[rootlocalhost ~]# cut -d : -f 1,3 /etc/passwd#以為分隔符提取第一第三列2.cut命令的局限[rootlocalhost ~]# df -h | cut -d -f 1,3#有空格時提取會出問題不能識別多個空格情況5.8.2 printf 命令[rootlocalhost ~]# printf ’輸出類型輸出格式’ 輸出內(nèi)容輸出類型%ns 輸出字符串。n是數(shù)字指代輸出幾個字符%ni 輸出整數(shù)。n是數(shù)字指代輸出幾個數(shù)字%m.nf 輸出浮點數(shù)。m和n是數(shù)字指代輸出的整數(shù)位數(shù)和小數(shù)位數(shù)。如%8.2f代表2位是小數(shù)8位是整數(shù)。 其中輸出格式選項有輸出格式控制字符作用\a輸出警告聲音\b輸出退格鍵也就是Backspace鍵\f清除屏幕\n換行\(zhòng)r回車也就是Enter鍵\t水平輸出退格鍵也就是Tab鍵\v垂直輸出退格鍵也就是Tab鍵5.8.3 awk 命令[rootlocalhost ~]# awk ‘條件1{動作1} 條件2{動作2}…’ 文件名條件Pattern 一般使用關系表達式作為條件 x 10 判斷變量 x是否大于10 x10 大于等于 x10 小于等于 動作Action 格式化輸出 流程控制語句 示例[rootzhangRabbitMQ zhang]# vi /tmp/student.txtid name java linux mysql 1 bilei 88 88 88 2 zhang 60 60 60[rootzhangRabbitMQ zhang]# awk {printf $2 \t $5 \n} /tmp/student.txtname mysql bilei 88 zhang 60BEGIN#awk BEGIN{printf This is a transcript \n } {printf $2 \t $6 \n} student.txEND# awk END{printf The End \n }{printf$2\t$6\n} student.txtFS內(nèi)置變量#cat /etc/passwd | grep /bin/bash | awk BEGIN {FS:} {printf $1 \t $3 \n}關系運算符#cat student.txt | grep -v Name | awk $6 87 {printf $2 \n }5.8.4 sed 命令sed 是一種幾乎包括在所有 UNIX 平臺包括 Linux的輕量級流編輯器。sed主要是用來將數(shù)據(jù)進行選取、替換、刪除、新增的命令。[rootlocalhost ~]# sed [選項] ‘[動作]’ 文件名選項-n 一般sed命令會把所有數(shù)據(jù)都輸出到屏幕 如果加入此選擇則只會把經(jīng)過 sed命令處 理的行輸出到屏幕。-e 允許對輸入數(shù)據(jù)應用多條sed命令編輯-i 用sed的修改結(jié)果直接修改讀取數(shù)據(jù)的文件 而不是由屏幕輸出 動作 a \ 追加在當前行后添加一行或多行。添加多行時除最后 一行 外每行末尾需要用“\”代 表數(shù)據(jù)未完結(jié)。 c \ 行替換用c后面的字符串替換原數(shù)據(jù)行替換多行時除最 后一行外每行末尾需“\”代 表數(shù)據(jù)未完結(jié)。 i \ 插入在當期行前插入一行或多行。插入多行時除最后 一行 外每行末尾需要“\”代 表數(shù)據(jù)未完結(jié)。 d 刪除刪除指定的行。 p 打印輸出指定的行。 s 字串替換用一個字符串替換另外一個字符串。格式為“行范 圍s/舊字串/新字串/g”和vim 中的替換格式類似。 示例[rootzhangRabbitMQ zhang]# vi /tmp/student.txtid name java linux mysql 1 bilei 88 88 88 2 zhang 60 60 60#查看文件的第二行[rootzhangRabbitMQ tmp]# sed 2p student.txtid name java linux mysql 1 bilei 88 88 88 1 bilei 88 88 88 2 zhang 60 60 60#只顯示第二行[rootzhangRabbitMQ tmp]# sed -n 2p student.txt1 bilei 88 88 88#刪除第二行到第四行的數(shù)據(jù)但不修改文件本身[rootzhangRabbitMQ tmp]# sed 2,3d student.txtid name java linux mysql5.9 字符處理命令5.9.1 排序命令 sort[rootlocalhost ~]# sort [選項] 文件名選項-f 忽略大小寫-n 以數(shù)值型進行排序默認使用字符串型排序-r 反向排序-t 指定分隔符默認是分隔符是制表符-k n[,m] 按照指定的字段范圍排序。從第n字段開始m字段結(jié)束默認到行尾 示例[rootlocalhost ~]# sort /etc/passwd#排序用戶信息文件[rootlocalhost ~]# sort -r /etc/passwd#反向排序[rootlocalhost ~]# sort -t : -k 3,3 /etc/passwd#指定分隔符是“”用第三字段開頭第三字段結(jié)尾排序就是只用第三字段排序[rootlocalhost ~]# sort -n -t : -k 3,3 /etc/passwd#指定分隔符是“”用第三字段開頭第三字段結(jié)尾排序以數(shù)值型進行排序5.9.2 wc 統(tǒng)計命令[rootlocalhost ~]# wc [選項] 文件名選項-l 只統(tǒng)計行數(shù)-w 只統(tǒng)計單詞數(shù)-m 只統(tǒng)計字符數(shù)