跟馬哥學linux (lesson 7)Bash腳本基礎知識

一、Linux程序分類:

1.守護進程(Daemon):開機自動啓動

常見linux後臺守護進程列舉:

amd:NFS守侯進程

apmd:高級電源治理

Arpwatch:記錄日誌並構建一個在LAN接口上看到的以太網地址和ip地址對數據庫

Autofs:自動安裝治理進程automount,與NFS相關,依靠於NIS

crond:linux下的計劃任務

Dhcpd:啓動一個DHCP(動態IP地址分配)服務器

Httpd:WEB服務器

Inetd:支持多種網絡服務的核心守候程序

Lpd:打印服務器

named:DNS服務器

netfs:安裝NFS、Samba和NetWare網絡文件系統

portmap:RPC portmap治理器,與inetd類似,它治理基於RPC服務的連接

routed:路由守候進程,使用動態RIP路由選擇協議

sendmail:郵件服務器sendmail

smb:Samba文件共享/打印服務

snmpd:本地簡單網絡治理候進程

squid:激活代理服務器squid

syslog:一個讓系統引導時起動syslog和klogd系統日誌守候進程的腳本

xfs:X Window字型服務器,爲本地和遠程X服務器提供字型集

xntpd:網絡時間服務器

ypbind:爲NIS(網絡信息系統)客戶機激活ypbind服務進程

yppasswdd:NIS口令服務器

ypserv:NIS主服務器

 

2.交互式進程:shell應用程序

shell程序組成部分:腳本或程序的源文件

 

二.linux編程的基本知識

1.編譯執行

處理過程分爲:預處理—>編譯—>彙編—>鏈接等4個過程 c或c++均採用此種方式

以C語言示例程序Hello World爲例演示過程

a.預編譯

image

b.編譯

image

c.彙編

image

d.鏈接

image

2.解釋執行:由解釋器全程參與運行過程,每次讀取一行,運行一行

Python:編程庫

            程序控制結構,調用編程庫完成程序編寫

            庫文件:功能模塊,在編程中調用:通過其API

例:使用Pthon打印hello world

image

image

Bash:編程

            程序控制結構,調用機器上命令程序文件運行程序編寫

            外部命令:個應用程序提供

例:使用bash shell打印hello world

image

image

3.兩種編程思想

其一爲:過程式編程,以指令爲中心,設計算法,數據服務於算法

其二爲:對象式編程,以數據爲中心,設計數據結構(類)程序服務於數據結構

 

三.詳解Bash編程

1.變量相關知識

變量的定義:可變的量,命令的內存空間

變量的生效範圍:

                本地變量:當前shell

                環境變量:當前shell及其自進程

                局部變量:某個函數執行過程

變量類型:

               數值,字符:

               數值:整數,浮點

               字符:ASCII

               位置參數變量:在腳本中傳遞給腳本的參數

               特殊變量:$? 打印上一個命令執行結果0爲正確執行1-255爲錯誤執行

                                  $* 參數個數

                                  $@ 參數個數

                                  $$ ppid

                                  $# 參數總數

                                  $1-n 第一到第n個參數

變量類型的作用:

               存儲空間,運算,存儲格式

語言對變量類型的支持力度:

              強類型:變量類型嚴格區分 C,Java等

              弱類型:變量類型不嚴格區分,默認存儲機制爲字符 Bash,Python等

bash的變量使用特點:弱類型,無需事先聲明

定義本地變量:

name=value

name:變量名

=:賦值符號

value:變量值

變量名:只能包含數字、字符和下劃線,且不能以數字開頭

引用變量 :${name} $name

引用類型:

弱引用:使用“”其內部的變量會替換爲變量值

image

強引用:使用'' 其內部不會發生變量替換

image

命令引用:`COMMAND`,$(COMMAND)引用變量執行的結果

image

聲明一個變量:declare -i name[=value]或let name=value

image

變量的生命週期:

            創建:執行name=value

            銷燬:自動銷燬 shell進程結束 手動銷燬unset name

image

環境變量定義:被導出的本地變量,生效範圍爲本shell及其派生的子shell

export name[=value]

declare -x name[=value]

查看所有環境變量:env printenv export set

銷燬:unset name

image

 

2.bash編程基礎

腳本:文本文件

        運行腳本:運行一個bash進程,此進程負責從腳本文件中讀取一個邏輯,由bash負責解釋和運行此邏輯

啓動腳本:

        (1)#bash /PATH/TO/SCRIPT_FILE

        (2)一個執行權限 #./PATH/TO/SCRIPT_FILE

格式:第一行:定格shebang

image

bash常用選項:-n檢查腳本語法

                            -x調試執行腳本

                            -v顯示詳細信息

image

3.bash測試邏輯

測試方式:

根據運行的命令的狀態結果

測試表達式:test [EXPR1] [EXRP2] 或 [ EXPR1 測試表達式 EXPR2 ]

 

整數測試:

$A -gt $B 是否大於

image錯誤返回

$A -ge $B  是否大於小於

image錯誤返回

$A -lt $B 是否小於

image正確返回

$A -le $B 是否小於等於

$A -eq $B 是否等於

$A -ne $B 是否不等於

 

字符串測試:

注:字符串比較字母排列的先後順序,字符串比較需要使用` `

“$A”> "$B":是否大於

image正確返回

“$A”<“$B”:是否小於

image

“$A”==“$B” 是否等於

“$B”!=“$B”是否不等於

image

-z "$A" 是否爲空,空則真

image

-n "$A" 是否爲非空,非空爲真

 

文件測試:測試文件的存在性以及屬性

-e|-a $file 是否存在,存在爲真

測試/etc/fstab是否存在

image

-f $file 文件是否存在且爲普通文件

測試/etc/fstab是否爲普通文件

image

-d $file 文件是否存在且爲目錄

測試/etc是否爲目錄

image

-h|-L $file 文件是否存在且爲符號連接文件

測試/dev/cdrom是否爲符號鏈接

image

-b $file 塊設備文件

測試/dev/sda1是否爲塊設備文件

image

-S $file socket文件

image

權限測試:

-r $file 存在且具有可讀權限

測試/etc/passwd是否有可讀權限

image

-w $file 存在且有可寫權限

測試/etc/passwd是否有可讀權限

image

-x $file 存在且有可執行權限

image

-u $file 存在且有suid權限

image

-g $file 存在且有sgid權限

-o $file 存在且有sticky權限

-O $file 當前用戶是否爲指定文件的屬主

-G $file 當前用戶是否爲指定文件的屬主

 

雙目操作符比較

$file1 -nt $file2 file1是否比file2新

image

$file1 -ot $file2 file1是否比file2舊

 

$file1 -ef $file2 file1和file2是否指向同一個inode即是否爲硬鏈接

imagehello爲hello.sh的硬鏈接指向同一個inode

image

3.bash條件判斷和循環語句

bash條件判斷(選擇執行)

語法格式:

if CONDITION;then if-true-分支;fi

image

if CONDITION;then if-true-分支 ;else if-else分支 ;fi

image

! CONDITION:取反

 

腳本參數(位置參數變量)

# ./script.sh /etc/fstab

$0 腳本本身

$1 第一個參數

$2 第二個參數

$n 第n個參數

image

shift可以對參數進行偏移

image

image

使用read命令可以實現交互式程序編寫

常用參數:-p 給出提示語句 -t 超時時間

image

循環語句:

for 循環列表;do 執行的操作;done

image

while 循環列表;do 執行的操作;done

image

image

until 循環列表;do 執行的操作;done

 

循環:將循環體代碼執行0,1或多次

進入條件:進入循環的條件

退出條件:循環終止的條件

for VAR in LIST;do 循環體;done

LIST:是由一個或多個空格或換行符分隔開的字符串組組成

 

組合測試條件:

條件間邏輯運算:

與:多個條件同時滿足

或:多個條件滿足其一即可

非:對指定的條件取反

表達式組合:

與:[ CONDITION1 -a CONDITION2 ]

image

或:[ CONDITION1 -o CONDITION2 ]

image

非:[ ! CONDITION ]

image

 

命令組合:

與:COMMAND1 && COMMAND2  其中&&爲短路與操作,即當COMMAND1正確執行後COMMAND2纔會被執行

image

或:COMMAND1 || COMMAND2 其中&&爲短路或操作,即當COMMAND1沒有被正確執行後COMMAND2纔會被執行

image

與:! COMMAND

 

case語句:

簡潔版的多分支if語句

使用場景:判斷某變量的值是否爲多分支的一種時使用

語法:

case $VAR in

PATTERN1)

分支1

;;

PATTERN2)

分支2

;;

PATTERNn)

分支n

;;

esac

輸入一個數,10和20均顯示false,50爲true

image

 

二、課堂練習

1、寫一個腳本:如果某路徑不存在,則將其創建爲目錄;否則顯示其存在,並顯示內容類型;(不要懷疑,就是這麼簡單)

2、寫一個腳本,完成如下功能;判斷給定的兩個數值,孰大孰小;給定數值的方法:腳本參數,命令交互;(使用read,依然如此簡單)

3、求100以內所有奇數之和(至少用3種方法。是的這是我們的作業^_^)

4、寫一個腳本實現如下功能:

(1) 傳遞兩個文本文件路徑給腳本;

(2) 顯示兩個文件中空白行數較多的文件及其空白行的個數;

(3) 顯示兩個文件中總行數較多的文件及其總行數;

5、寫一個腳本

(1) 提示用戶輸入一個字符串;

(2) 判斷:

如果輸入的是quit,則退出腳本;

否則,則顯示其輸入的字符串內容;

6、寫一個腳本,打印2^n表;n等於一個用戶輸入的值;(不好意思,我調皮了)

7、寫一個腳本,寫這麼幾個函數:函數1、實現給定的兩個數值的之和;函數2、取給定兩個數值的最大公約數;函數3、取給定兩個數值的最小公倍數;關於函數的選定、兩個數值的大小都將通過交互式輸入來提供。

解答:

1.

#!/bin/bash    
aaa="/etc/aaa"   
if [ ! -e "$aaa" ]     
  then mkdir $aaa && echo "create successful."     
  else echo "$aaa has exist." && ls -l $aaa     
fi

image

2.

#!/bin/bash    
if [ $# -ne 2 ];then echo "Plz enter 2 numbers.";fi     
if [ $1 -gt $2 ];then echo $1 ">" $2     
  elif [ $1 -lt $2 ];then echo $1 "<" $2     
  elif [ $1 -eq $2 ];then echo $1 "=" $2     
  else echo "unkonw."     
fi

image

3.

方法一、

#!/bin/bash    
declare -i i     
declare -i sum=0     
for i in {1..100}     
  do if [ $(($i%2)) -ne 0 ];then sum=$i+$sum;fi     
done     
echo $sum

image

方法二、

#!/bin/bash    
declare -i aaa     
declare -i sum=0     
for aaa in `seq 1 2 100`     
  do sum=$aaa+$sum     
done     
echo $sum

image

方法三、

#!/bin/bash    
declare -i i     
declare -i sum=0     
declare -i oddsum=0     
declare -i evensum=0     
for i in {1..100}     
  do sum=$i+$sum     
    if [ $(($i%2)) -eq 0 ];then oddsum=$oddsum+$i;fi && evensum=$sum-$oddsum     
done     
echo $evensum

image

4.

#!/bin/bash    
if [ $# -ne 2 ]     
  then echo "Plz enter 2 files"     
  else sumline1=`cat $1|wc -l` sumline2=`cat $2|wc -l` blank1=`grep '^$' $1|wc -l` blank2=`grep '^$' $2|wc -l`     
    if [ $blank1 -gt $blank2 ];then echo "more blank line is $1 $blank1 lines"     
       else echo "more blank line is $2 $blank2 lines"     
    fi     
    if [ $sumline1 -gt $sumline2 ];then echo "more line is $1 $sumline1 lines"     
       else echo "more line is $2 $sumline2 lines"     
    fi     
fi

image

5.

#!/bin/bash    
while true     
do     
read -t 5 -p "Plz enter someting. " aaa     
  if [ $aaa == "quit" ];then exit     
    else echo $aaa     
  fi     
done

image

6.注:(次題目參考了@謝俊同學,並略加修改。)

[object Object]
#!/bin/bash
#
read -t 5 -p "please enter a number: " x
[ -z $x ]&&echo "Errot:please enter a number!"
count=2
for i in $(seq 0 $x);do
    if [ $i -eq 0 ];then
       echo -e $((2**$i))
    elif [ $i -eq 1 ];then
       echo -e $((2**$i))
    elif [ $i -gt 1 ];then
    count+=x2              # 字符的自加,感謝“天真的小同志”的指導
    echo $count=$[2**$i]
    else echo "Error:please enter a number!"
    fi
done
7.
#!/bin/bash
#
sum() {
read -p "Plz enter two number. " args1 args2
echo sum=$((args1+args2))
}

gcd() { #先求出其中任意兩個數的最大公約數,再求這個最大公約數與第三個數的最大公約數,依次求下去,直到最後一個數爲止。
read -p "Plz enter two number. " a b
c=$((a%b)) #對a,b進行取模運算
while [ "$c" -ne 0 ];do #當a,b的模不等於0時
gcd=$c #對gcd進行第一次賦值,gcd等於a,b的模
a=$b  #把上一次b的至賦給a
b=$c  #把上一次c的值賦給b
c=$((a%b)) #再一次進行取模,一直進行循環直到c的值爲0
done
echo "gcd=$gcd"
}

lcm() { #最小公倍數爲兩個數的乘機除以最大公約數
read -p "Plz enter two number. " a b
c=$((a%b))
pro=$((a*b))
while [ "$c" -ne 0 ];do
gcd=$c
a=$b
b=$c
c=$((a%b))
done
echo "lcm=$((pro/gcd))"
}
case $1 in
sum)
sum
;;
gcd)
gcd
;;
lcm)
lcm
;;
*)
echo "Plz Usage `bashname`{sum|gcd|lcm}"
;;
esac

wKioL1X6PpjAPWkKAAErfdk7sx8471.jpg

wKiom1X6PGCwF_gjAAFBrjBcsys436.jpg

wKioL1X6PpjxW9MSAAD8pDlmoJ0046.jpg


發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章