shell脚本基础

目录

一、概述

二、shell脚本基础概念和语法

三、表达式

四、shell脚本编写


一、概述

(一)Shell脚本介绍

Shell脚本是一种用于自动化执行命令和任务的脚本语言。它是在操作系统的命令行界面下运行的,通过编写一系列的命令和逻辑来完成特定的任务。Shell脚本可以用于各种操作系统,如Linux、Unix和Mac OS等。

Shell脚本是一种强大的工具,它可以帮助用户简化重复性的任务,提高工作效率。通过编写Shell脚本,用户可以将一系列的命令和操作组合在一起,形成一个可执行的脚本文件。这样,用户只需要运行这个脚本文件,就能够自动执行其中的命令,完成特定的任务。

Shell脚本的语法相对简单,主要由一系列的命令和控制结构组成。用户可以使用各种命令来完成不同的操作,如文件操作、文本处理、系统管理等。同时,Shell脚本还支持条件判断、循环和函数等控制结构,使得用户能够编写更加复杂和灵活的脚本。

(二)Shell脚本的作用

Shell脚本的作用是通过编写一系列的命令和脚本语句,来实现自动化的任务处理和系统管理。Shell脚本可以用于执行各种操作系统命令、管理文件和目录、处理文本数据、调用其他程序等。通过编写Shell脚本,可以提高工作效率,简化重复性的操作,减少人工干预,实现自动化的任务处理。同时,Shell脚本也是学习和理解操作系统的重要途径,可以深入了解操作系统的底层原理和机制。无论是系统管理员、开发人员还是普通用户,都可以通过学习和使用Shell脚本来提高工作效率和解决问题。

(三)Shell脚本的优势

1. 简单易学:Shell脚本语法简洁,易于理解和学习。即使没有编程经验的人也可以快速上手,编写出功能强大的脚本。

2. 强大的命令行工具:Shell脚本可以调用系统的各种命令行工具,如grep、sed、awk等,使得脚本能够处理各种文本文件、日志文件等。

3. 自动化任务:Shell脚本可以用于自动化执行一系列的任务,如备份文件、定时执行任务、批量处理数据等。通过编写脚本,可以节省大量的时间和精力。

4. 灵活性:Shell脚本可以根据不同的需求进行定制和扩展。可以通过变量、条件判断、循环等控制结构来实现不同的逻辑和功能。

5. 跨平台性:Shell脚本可以在不同的Unix和类Unix系统上运行,如Linux、Mac OS等。这使得脚本具有很好的可移植性,可以在不同的环境中使用和分享。

(四)shell应用场景

重复性操作

交互性任务

批量食物处理

服务运行状态监控

定时任务执行

二、shell脚本基础概念和语法

  1. 注释:注释用于在脚本中添加说明和解释。以#字符开头的行被视为注释,将被解释器忽略。

  2. 变量:变量用于存储数据。变量的命名区分大小写,通常使用大写字母。通过variable_name=value来设置变量的值,使用$variable_name来引用变量的值。

  3. 字符串:字符串是由字符组成的文本。可以使用单引号或双引号来定义字符串。双引号内的字符串可以包含变量和转义字符,而单引号内的字符串则原样输出。

  4. 输入输出:使用echo命令输出文本,使用read命令从用户获取输入。

  5. 基本运算:shell支持基本的数学运算,例如加法、减法、乘法和除法。

  6. 条件语句:使用if语句进行条件判断。if语句根据条件的真假来执行不同的代码块。

  7. 循环语句:使用for循环和while循环来执行重复的任务。for循环可以遍历列表或范围,而while循环在条件为真时执行。

  8. 函数:函数是一组被封装的代码块,可以在脚本中多次调用。使用function_name() { ... }来定义函数,使用function_name来调用函数。

  9. 条件测试:可以使用test命令或方括号进行条件测试。例如,if [ $a -eq $b ]用于比较两个变量的值是否相等。

三、表达式

(一)shell

shell命令解释环境

类型
        sh
        ash
        bsh
        csh
        bash
        tcsh
        dsh
        zsh

查看系统中支持的shell

cat /etc/shells

查看系统默认shell

echo $SHELL

(二)变量

一)组成

1、变量名

不会变化

声明规范:不能是数字或数字开头;以_或字母开头;变量名中不能包含特殊字符

声明方法:

驼峰式   userName

双驼峰   UserName

shell写法:user_name;username;USERNAME

2、变量值

不断变化

承载的物体

数字、字符

二)类型

1、系统内置变量(环境变量):env

2、自定义变量:

varName=varValue   

等号两边不能有空格

数字:var1=1

字符串:shell中可以不使用引号    当包含有空格时,需要使用引号

引号的用法:

不会引用变量值    单引号       

会应用变量值    双引号     "   

引用命令结果    反撇号    `

$(命令)    应用场景较多

3、位置变量:

脚本后参数所在的位置:$1 ...  $9

预定义变量:

$0    脚本本身的名称

$#     脚本后参数的个数

$*    脚本运行时参数的内容(整体输出)

$@   脚本运行时参数的内容(逐个输出)

$?    脚本运行完毕后的返回值,默认情况  0  成功,非0 失败

三)作用域

默认变量只在当前shell下生效

若要在当前及其子shell下生效,需要声明为全局变量:export

四)输出:echo $varName

五)shell中的字符串:string

赋值: str1=foodfornoting.gpg

1、获得字符串的长度

语法:    ${#StringName}

案例:    echo ${#str1}

输出结果:17

2、字符串取子串

语法:    ${#StringName:position:lenght}

案例:    echo ${str1:0:3}

输出结果:foo

注意:lenght没有定义时,一直取到字符串的结尾!

3、字符串的截取

a)从左至右截取最后一个匹配字符串string之后的所有字符串

语法:    ${StringName##*string}

案例:    echo ${str1##*fo}

输出结果:rnoting.gpg

b)从左至右截取第一个匹配字符串string之后的所有字符串

语法:${StringName#*string}

案例:    echo ${str1#*fo}

输出结果:odfornoting.gpg

c)从右至左截取最后一个匹配字符串string之后的所有字符串

语法:    ${StringName%%string*}    

案例:    echo ${str1%%o*}

输出结果:f

d)从右至左截取第一个匹配字符串string之后的所有字符串 

语法: ${StringName%string*}       

案例: echo ${str1%o*}

输出结果:foodforn

4、字符串的拼接

语法: StringName3=${StingName1}${StringName2}

案例:str1=Hello

str2=,Jack!

str3=${str1}${str2}

echo ${str3}

输出结果: Hello,Jack!

5、字符串替换:

语法:    ${StringName/OldString/NewString}

案例:    str1=foodfornoting.gpg

echo ${str1/oo/kk}

输出结果:fkkdfornoting.gpg

(三)运算符

一)数学运算   + - * / %   * 作为乘号时需要加转义符\

运算方法

expr

expr $a + $b

$((a+b))

echo $((a+b))

$[a+b]

echo $[a+b]

注意  shell不支持浮点数的显示

二)比较运算

1、数值比较

            -eq     等于
            -ne     不等于
            -lt       小于
            -le      小于等于
            -gt      大于
            -ge     大于等于

2、字符串比较

            =           字符串一致
            !=          字符串不一致
            -z          字符串为空
            !     -z    字符串不为空

3、文件比较

            -e   文件或目录是否存在
            -f    是否为文件
            -d   是否为目录
            -r    判断文件是否可读
            -w   判断文件是否可写
            -x    判断文件是否可执行

三)逻辑运算符

&&

[ $a -ne $b ] &&  echo OK    条件 && 输出结果   条件为真输出

||

[ $a -ne $b ] ||  echo OK    条件 || 输出结果    条件为假输出

-a  并且,有假则假,全真为真

-o  或者,有真则真,全假为假

!  取反 有真则假,有假则真

四、shell脚本编写

(一)shell脚本编写规范

第一行  #!/bin/bash

第二行  #脚本的说明

第三行   脚本正文

(二)shell运行规则

没有x权限   

bash  脚本所在路径/脚本文件

source 脚本所在路径/脚本文件

.      脚本所在路径/脚本文件

脚本存在cd  时,会切换到目标目录

有x权限

./脚本文件

脚本绝对路径/脚本文件

(三)shell脚本运行追踪

bash -x 脚本所在路径/脚本文件

(四)read -p "提示语" 变量名      读取键盘输入并赋值给变量名

(五)语句

1)条件语句

1、单分支if

if [ ];then

fi

2、双分支if

if [ ];then

else

fi

3、多分支if

if [ ];then

elif [ ];then

else

fi

2)循环语句

1、for

for 条件(i in 值)|((i=1;i<=10;i++))

do

语句

done

2、while

i=1

while 条件

do                                                                                                                                                     

语句                                                                                                                                                 

let  i++

done

关于$*与$@的验证

3)开关语句

1、case

case $1 in

条件1)

    语句

;;

条件2)

   语句

;;

*)

   帮助信息

;;

esac

(六)文件操作四剑客

1)正则表达式

1、基础正则

创建test.txt


a)查找特定字符
cat test.txt | grep -n 'test'


b)利用[]查找集合字符
cat test.txt | grep -n 'sh[io]rt'    匹配i或者o


cat test.txt | grep -n '[^w]'         排除w


cat test.txt | grep -n '[a-h]oo'


cat test.txt | grep -n '[0-9]'   加点数字


c)查找行首"^"与行尾"$" 
cat test.txt | grep -n '^[A-Z]'


cat test.txt | grep '\.$'      \ 为转义符    .为任意符


d)查找任意一个字符"."与重复字符"*"
cat test.txt | grep -n 'w..d'


cat test.txt | grep -n 'ooo*'


e)查找连续的字符范围"{}",需要使用转义符,"\{\}"
cat test.txt | grep -n 'o\{2\}'


cat test.txt | grep -n 'wo\{2,5\}d'


cat test.txt | grep -n 'wo\{2,\}d'

2、扩展正则
a)+,重复一个或一个以上的前一个字符
cat test.txt | grep -nE 'wo+d' 或者  cat test.txt | egrep -n 'wo+d'


b)?,零个或者一个前一个字符
cat test.txt | egrep -n 'bes?t'


c)|,使用或者的方式找出多个字符
cat test.txt | egrep -n 'of|is|on'


d)(),查找组字符串
cat test.txt | egrep -n 't(a|e)st'


e)()+,辨别多个重复的组
cat test.txt | egrep -n 'A(xyz)+C'

 

3、常见正则表达式

数字
                “^[0-9]*[1-9][0-9]*$” //正整数  
                “^((-\d+)|(0+))$” //非正整数(负整数 + 0)  
                “^-[0-9]*[1-9][0-9]*$” //负整数  
                “^-?\d+$” //整数 
                “^\d+(\.\d+)?$” //非负浮点数(正浮点数 + 0)  
                “^(([0-9]+\.[0-9]*[1-9][0-9]*)|([0-9]*[1-9][0-9]*\.[0-9]+)|([0-9]*[1-9][0-9]*))$” //正浮点数 
                “^((-\d+(\.\d+)?)|(0+(\.0+)?))$” //非正浮点数(负浮点数 + 0) 
                “^(-?\d+)(\.\d+)?$” //浮点数 

字符串
                “^[A-Z]+$” //由26个英文字母的大写组成的字符串  
                “^[a-z]+$” //由26个英文字母的小写组成的字符串  
                “^[A-Za-z0-9]+$” //由数字和26个英文字母组成的字符串  
                “^\w+$” //由数字、26个英文字母或者下划线组成的字符串

Email
“^[\w-]+(\.[\w-]+)*@[\w-]+(\.[\w-]+)+$” //email地址  
“^([w-.]+)@(([[0-9]{1,3}.[0-9]{1,3}.[0-9]{1,3}.)|(([w-]+.)+))([a-zA-Z]{2,4}|[0-9]{1,3})(]?)$”   //Email 

Url 
“^[a-zA-z]+://(\w+(-\w+)*)(\.(\w+(-\w+)*))*(\?\S*)?$” //url 

IP
“^(d{1,2}|1dd|2[0-4]d|25[0-5]).(d{1,2}|1dd|2[0-4]d|25[0-5]).(d{1,2}|1dd|2[0-4]d|25[0-5]).(d{1,2}|1dd|2[0-4]d|25[0-5])$”   //IP地址

Tel 
/^((\+?[0-9]{2,4}\-[0-9]{3,4}\-)|([0-9]{3,4}\-))?([0-9]{7,8})(\-[0-9]+)?$/     //电话号码

日期校验
/^(d{2}|d{4})-((0([1-9]{1}))|(1[1|2]))-(([0-2]([1-9]{1}))|(3[0|1]))$/   //  年-月-日    yyyy-MM-dd / yy-MM-dd 格式
"^[0-9]{4}-((0([1-9]{1}))|(1[1|2]))-(([0-2]([0-9]{1}))|(3[0|1]))$"   // 年-月- 日  yyyy-MM-dd 格式
/^((0([1-9]{1}))|(1[1|2]))/(([0-2]([1-9]{1}))|(3[0|1]))/(d{2}|d{4})$/   // 月/日/年

2)grep进阶

选项
            -r
                递归扫描指定目录下的每一个文件
            -l
                只显示匹配到指定关键字的文件名,而不是文件内容
案例
查看/etc目录下所有包含bash的文件名
grep -rl bash /etc

3)egrep     完美支持正则表达式

4)find进阶

按照权限查找
-perm

按照时间戳查找
-atime
-mtime
-ctime
-exec
find /var/spool/mail -type f -exec rm -rf {} \;
xargs
find /var/spool/mail -type f | xargs rm -rf

5)sed

语法
            sed [选项] '操作' 参数 
            sed [选项] -f scriptfile 参数

选项
            -e:表示用指定命令或脚本处理
            -f:指定脚本文件
            -h:帮助
            -n:表示仅显示处理后的结果
            -i:直接编辑文本文件
            -r:支持扩展正则
            重点

操作
            a:增加,在当前行下面以行增加指定内容
            c:替换,将选定行替换
            d:删除,删除指定行
            i:插入,在选定行的上面插入一行
            p:打印
            s:替换,替换指定字符
            y:字符转换
            重点

案例:

1.输出符合条件的文本:
sed -n 'p' test.txt     #相当于cat


sed -n '3p' test.txt    #打印第3行


sed -n '3,6p' test.txt    #打印第3到6行的内容


sed -n 'p;n' test.txt    #打印奇数行


sed -n 'n;p' test.txt    #打印偶数行


sed -n '1,6{p;n}' test.txt    #打印1到6行之间的奇数行


sed -n '5,${p;n}' test.txt    #从第5行开始打印奇数行


sed -n '/the/p' test.txt    #匹配the


sed -n '5,/the/p' test.txt     #匹配从第5行开始到包含the的行


sed -n '/the/,10p' test.txt     #匹配从包含the的行到第10行结束


sed -n '/the/=' test.txt    #打印包含the的行号

 

2.删除符合条件的文本
nl test.txt | sed '3d'    #删除第3行
nl test.txt | sed '3,5d'
nl test.txt | sed '/the/d'    #删除the所在行

3.替换符合条件的文本
nl test.txt | sed 's/the/TTTTTT/'    #替换全文本
nl test.txt | sed '4s/the/TTTTTT/'    #替换第4行
nl test.txt | sed 's/l/L/2'        #替换匹配到的第2个l

4.迁移符合条件的文本
H:复制;g:覆盖;G:追加行;w:保存;r:读取;a:追加内容
sed '/the/{H;d};$G' test.txt #匹配the所在行并迁移至文件末尾
sed '3aTest' test.txt #在第3行下面新建行并写入Test
sed '/the/aTest' test.txt #匹配the所在行并在下一行写入Test

5.使用脚本编辑文件内容
vim opt.txt
1,5H
1,5d
16G
sed -f opt.txt test.txt    #将1到5行迁移至16行后
6.以上修改想要直接修改文本源文件,只需要加入选项"-i"

6)awk

语法
awk 选项 '模式或条件{编辑命令}' 文件1 文件2 ...
awk -f 脚本文件 文件1 文件2 ...

选项: -F
            指定每行的分隔符
            默认分隔符为空格

内建变量
            FS:指定每行的分隔符
            NF:指定当前处理行的字段个数
            NR:当前处理行的行号
            $0:当前处理行的整行内容
            $n:当前处理的第n个字段
            FILENAME:处理文件名
            RS:数据记录分隔,默认是\n

案例:

a)按行输出
awk '{print}' test.txt          #等同cat 
awk 'NR>=1&&NR<=3{print}' test.txt 
awk 'NR==1,NR==3{print}' test.txt #打印1到3行
awk 'NR%2==0{print}' test.txt     #打印偶数行

b)按段输出
默认以"空格"分段!

ifconfig ens33 |awk '/netmask/{print $2}' #筛选IP地址

cat /etc/shadow | awk -F : '$2=="!!"{print $1}' #打印不能登录系统的用户

c)调用shell命令
cat /etc/passwd | awk -F : '/bash$/{print | "wc -l"}' /etc/passwd     #统计能够登录系统的用户个数       

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值