首页 > 运维 > linux运维 > 正文

一文掌握shell脚本的基本语法

看不見的法師
发布: 2025-07-15 10:34:55
原创
723人浏览过

欢迎大家star我的github:https://github.com/solerho/geeks-shell,建议直接使用github来查看排版,发现markdown有错位的情况。

00. 使用环境和说明centos8 Kernel 4.18.0-305.12.1.el8_4.x86_64x86_64 GNU/Linuxbash 版本:4.4.20本文不介绍和Linux 指令相关的内容先修内容:Linux基本命令(推荐书籍:《鸟哥Linux私房菜:基础学习》)只介绍本人在场景中使用后,结合参考书籍做的一个学习笔记,未使用过的暂时不更新部分图片来源书籍《高级Bash脚本编程指南》所有笔记的内容均可通过 cmd --help 查看具体的用法01. shell概述

在shell中,每个脚本的开头都使用 #! ,就是告知系统文件的执行都需要指定一个解释器。指定一个文件类型的特殊标记。占用 2 字节

1.1 脚本解释器

shell极脚本都是以 #!开头,告知系统该文件的执行需要一个解释器。

常见的解释器类型如下:

代码语言:txt复制
<code class="txt">#!/bin/sh#!/bin/bash#!/usr/bin/perl#!/usr/bin/tcl#!/bin/sed -f#!/usr/awk -f</code>
登录后复制

解释说明

#!/bin/sh linux系统上默认是bash,多数UNIX商业OS中也默认shell。1.2 调用脚本

执行脚本的三种方式:

代码语言:txt复制
<code class="txt">#方式1sh helloworld.sh#方式2bash helloworld.shbash +x helloworld.sh</code>
登录后复制

第三种方式有一点特殊

代码语言:txt复制
<code class="txt">./helloworld.sh             #需给文件授予执行权限#实授予权限的方式如下chmod +x helloworld.sh      #授予可执行权限chmod +rx helloworld.sh     #授予任何人可执行可读和可执行权限chmod u+rx helloworld.sh    #只给脚本的所有者可读和可执行权限</code>
登录后复制
1.3 第一个脚本helloworld代码语言:txt复制
<code class="txt">#!/bin/bashecho "helloworld"</code>
登录后复制

目前Linux/unix系统中,普遍的shell脚本的第一行是:#!/bin/sh 或者 #!/bin/bash

1.4 Linux管道

在Linux中可以将两个或者多个命令连接到一起的符号(|),称为管道符

思想:把上一个命令的输出作为下一个命令的输入(也就是因连接而形成管道(pipe)概念)。

语法格式:

代码语言:txt复制
<code class="txt">command_1 | command_2 | ... | command_N# 最简单的管道cat helloworld.sh | grep hello</code>
登录后复制

⚠️注意:有输出才能输入,所以输出出现错误,则输入部分将无法处理。

管道的应用:在greptailcatsedawk等Linux命令中较为常见。

02. shell中特殊字符

特殊字符

功能

说明

注意

#

1.注释2.声明命令解释器的类型3.某些特定的模式匹配操作使用

1.注释方面:一般是行首中以 #作为开头2.声明解释器类型一般是在脚本第一行使用格式:#!/bin/bash

命令不能和注释在同一行上,也就是注释的后面

;

命令分隔符,可以在同一行上写多个命令

某些情况需要使用转义符转义

;;

双分号,终止case选项

.

bash内置命令

1.点(.)放在文件名前面表示隐藏文件。2.移动文件操作时,如果是单独点作为参数cp cxx/helloworld.sh .表示当前工作目录3.两个点(..),表示上一级目录。4.正则表达式中作为匹配任何的单个字符

" "

双引号表示字符串

' '

单引号表示字符

,

逗号操作符

链接一系列操作

|反斜杠()|对单个字符的引用机制|一般用来转义双引号(" ")单引号(' ')。||

/

正斜杠(/)

1.作为文件名路径分隔符/data/cxx/Makefile2.用作除法算术操作符

*

1.乘法算术操作符2.两个(**)表示求幂运算符3.通配符,可以用来匹配给定目录下的任何文件名

?

1.测试通配符2.通配符,在正则表达式中表示一个字符,也可以用来匹配单个字符。

在表达式中测试一个条件的结果,类似C语言中的三元操作符。

$

1.引用变量2.正则表达式中,表示行结束符

${}

参数替换

$* or $@

位置参数

$$

进程ID变量

保存所在脚本的进程ID

$?

退出状态码变量

可保存命令、函数或者脚本本身的退出状态码

一般是01

{ }

大括号,代码块,也叫作内部组。

在函数或者判断语句中使用代码块

在大括号中不允许有空白,除非空白被引用或者转义

[ ]

1.测试条件2.数组元素 3.字符范围

作为字符范围时,方括号描述一个匹配的字符范围

> &> >& >>

重定向

03. 转义符

转义符是一种引用单个字符的方法。添加转义符() 使得shell中的某个字符失去原有特殊含义。

注意:在echosed 中谨慎使用转义符,否则会有相反效果。

转义符

含义

实例

表示新的一行

echo "first line";echo $' ';echo "third line"

表示回车

表示水平制表符

表示垂直制表符



表示后退符



表示"alert" (蜂鸣器或闪烁)

xx

转换为八进制的ASCII码,等价于0xx

"

表示双引号

$

表示$本身的意思,跟在后面的变量名不会起作用

echo "$variables~~~~"

\

表示反斜线

echo "\" #结果为 ||

赋值给变量的字符串的元素也会被转义, 但是不能把一个单独的转义符赋值给变量。

04. shell中参数:$0$?$!$$$*$#$@

字符符号

功能(用途)

$0

shell文件本身的文件名

$1~$n

添加到Shell的各参数值$1是第1参数、$2是第2参数、…、$n表示第n个参数。⚠️注意:10以上要用大括号,如{10}。

$?

最后运行命令的结束代码(返回值),执行成功返回0不成功则返回非零值(一般解释为错误码)

$$

Shell本身的PID(ProcessID)

$!

Shell最后运行的后台Process的PID

$-

使用Set命令设定的Flag一览

$*

所有参数列表。如 "$*"用「"」括起来的情况、以"$1 $2 … $n" 的形式输出所有参数。

$@

所有参数列表。如 "$@"用「"」括起来的情况、以"$1" "$2" … "$n" 的形式输出所有参数。

$#

添加到Shell的参数个数

$*$#区别

不被双引号包含时,两者没有区别。当被双引号包含时, $* 是将所有参数看作一整个数据。而 $# 则是将每个参数看作一个数据

具体实例脚本:

代码语言:txt复制
<code class="txt">#!/bin/bash# 已进行shellcheck检查echo "This is $0 ---- : $0"echo "This is $1 ---- : $1"echo "This is $2 ---- : $2"echo "This is $? ---- : $?"echo "This is $$ ---- : $$"echo "This is $! ---- : $!"echo "This is $_ ---- : $_"echo "This is $* ---- : $*"echo "This is $@ ---- : $*@"echo "This is $# ---- : $#"</code>
登录后复制

直接执行且打印信息如下:

代码语言:txt复制
<code class="txt">bash +x paramshell.sh 7 77#打印信息This is $0 ---- : paramshell.sh         # 显示文件名This is $1 ---- : 7                     # 第1个参数This is $2 ---- : 77                    # 第2个参数This is $? ---- : 0                     # 执行完毕后的返回值 0 --- True,1 --- FalseThis is $$ ---- : 1549879               # 该程序执行时的本身进程IDThis is $! ---- :                       # shell后台运行的进程IDThis is $_ ---- : This is $! ---- :     # 变量保存之前执行命令的最后一个参数的值This is $* ---- : 7 77                  # 参数值列表This is $@ ---- : 7 77                  # 参数值列表This is $# ---- : 2                     # 参数的个数</code>
登录后复制
5. 变量问题

变量表示数据的方法。是计算机为了保存数据项而在内存中分配的一个位置或一组位置的标识或名字。

变量名就是保存值的地方

5.1 shell变量概述

shell变量有系统变量和自定义变量两种。

对于变量名的声明规则类似于其他编程语言。由字母、数字、下划线组成,但不能以数字开头。

代码语言:txt复制
<code class="txt">hello_123       # 合法123_hello       # 不合法</code>
登录后复制
5.2 内部变量(系统变量)

主要记录实际工作中使用的,也不要记住。用到了再查即可。

系统变量

说明

实操

备注

$BASH_VERSION

查看bash的版本

echo $BASH_VERSION

$BASH

bash的二进制程序文件的路径

echo $BASH

$USER

当前用户

echo $USER

一般是root

$EUID

有效用户ID

echo $EUID

$EUID 不一定与$UID相同

$FUNCTION

在函数中,可直接打印当前函数的名字

$GROUP

当前用户所属的组

echo $GROUP

一个组ID列表

$HOSTNAME

当前主机名字

echo $HOSTNAME

$HOSTTYPE

当前主机类型

echo $HOSTTYPE

$PATH

可执行文件的搜索路径

echo $PATH

以冒号分隔的目录列表

pwd

当前工作目录

pwd

5.3 自定义变量基本语法定义变量:变量名=变量值,等号两侧不能有空格(与其它语言可设空格的区别之处)。变量名一般习惯使用大写。设置变量:set 变量名=变量值。删除变量:unset 变量名=变量值。声明静态变量:readonly 变量名,静态变量不能用unset使用变量:$变量名变量赋值简单赋值:a=123 && echo $a命令行赋值给变量#使用反引号str=`cat helloworld.sh`#直接使用 $(..)格式os=$(cat /etc/os-release)局部变量:只在代码块或函数中可见可用。外部不可用。Bash变量:不区分类型,都是字符串,不允许进行数值计算,除非变量中包含数字。如果变量的值中间有空格,则使用引号(单引号或双引号均可)扩起来。5.4 环境变量

会影响用户接口和shell的行为。环境变量是一个全局变量。

通过 export 命令将变量声明为环境变量即可。

代码语言:txt复制
<code class="txt">export 变量名=变量值# 方式 1 :直接export导入,命令行窗口重启后失效export LD_LIBRARY_PATH=/usr/local/cuda/lib# 方式 2# 加入到 root目录下的 .bashrc 中# 使用 source ./bashrc 使修改后的配置信息生效,命令行窗口重启或者机器重启均不会失效# 查看环境变量是否生效echo $变量名echo $LD_LIBRARY_PATH</code>
登录后复制

对于环境变量的查看

代码语言:txt复制
<code class="txt"># 方式 1 :查看所有变量(包括环境变量和自定义变量)set# 方式 2 :只能查看环境变量env</code>
登录后复制
5.5 引用变量

引用:将字符串使用双引号扩起来。作用:保护字符串的特殊字符(通配符)不被shell重新解释或者扩展。

代码语言:txt复制
<code class="txt">[root@centos8 data]# var01=3[root@centos8 data]# echo $var013</code>
登录后复制

在引用变量时,需要使用$来进行引用变量的值。

变量在使用过程中,如果没有$作为前缀,需要思考如下情况:

被声明或被赋值。是否被unset被使用export方式导入是否作为信号量。赋值的两种方式:- 使用 = 方式。- 直接使用read命令。6. 运算符6.1 赋值运算符符

=: 通用赋值操作符,可用于算术和字符串的赋值。

6.2 算术运算符

运算符

描述

备注

+

加法

延伸 +=

-

减法

延伸 -=

*

乘法

延伸 *=

**

求幂

/

除法

延伸 /=

%

求模(余数)

延伸 %=

++

自增

a++ 等于 a = a + 1

--

自减

a-- 等于 a = a - 1

⚠️注意:运算符(+|-|*|/|%)= 表示:将变量的值(+|-|*|/|%)另一个常量值,然后再将结果赋值给变量。

具体实例:

代码语言:txt复制
<code class="txt">#!/bin/bash# 未进行shellcheck检查a=5let a+=2echo "plus : $a "       # a = 7 和let a-=2echo "minus : $a"       # a = 5 差let a*=2echo "multi : $a"       # a = 10 积let a/=2echo "div : $a"         # a = 5 商let a%=2echo "Modulo : $a"      # a = 1 余数</code>
登录后复制
6.3 位运算符

使用较少,暂时不做更新学习。

6.4 比较运算符

运算符

英文全称

中文描述

示例

-eq

equal

等于

1 -eq 1 为 true

-ne

not equal

不等于

1 -ne 1 为 false

-gt

greater than

大于

2 -gt 1 为 true

-lt

lesser than

小于

2 -lt 1 为 false

-ge

greater or equal

大于或等于

2 -ge 1 为 tbnrue

-le

lesser or equal

小于或等于

2 -le 1 为 false

6.5 逻辑运算符

运算符

描述

等价使用

具体说明

&&

逻辑与(AND)

-a

需两个为True

||

逻辑或(OR)

-o

其中之一为True

7. 操作字符串

字符串是由单引号('') 或者 双引号("") 或者也可不用引号。

单引号原样输出(变量依然原样输出)单引号内不能再使用单引号。双引号代码语言:txt复制
<code class="txt">- 如果其中使用了变量,则变量内容也会被替换。- 如果再次使用引号,则使用转义符。</code>
登录后复制
不用引号 性质和双引号一致,但是字符串不能有空格。7.1 字符串的长度

直接使用 ${#string} 来计算字符串的长度

代码语言:txt复制
<code class="txt"># 3 个语法格式${#string}              # 方式 1expr length $string     # 方式 2expr "$string" : '.*'   # 方式 3# 具体实例str="hello world"echo "After using #str : ${#str}"echo "Use expr length : $(expr length "$str")" # 该方式不建议使用,因为shellcheck也建议使用第一种方式echo "Use expr : $(expr "$str" : '.*')"</code>
登录后复制
7.2 索引子串第一次出现的位置代码语言:txt复制
<code class="txt"># 语法格式 : expr index "$string" '$substring'# 详细实例 ---- 未进行shellcheck检查str="SolerHO123456"echo $(expr index "$str" H) # 结果为 6</code>
登录后复制
7.3 提取子串

目的:提取一些特殊需求的字符。

语法

法语写作助手
法语写作助手

法语助手旗下的AI智能写作平台,支持语法、拼写自动纠错,一键改写、润色你的法语作文。

法语写作助手 31
查看详情 法语写作助手

说明

${string:position}

在string中从位置position开始提取子串

${string:position:length}

在string中从位置position开始提取 length长度的字串

7.4 子串截除
一文掌握shell脚本的基本语法子串截除.png
7.5 子串替换
一文掌握shell脚本的基本语法子串替换.png
7.58. 数组

bash支持只支持一维数组。数组元素可使用符号 var[number] 来初始化。

脚本使用 declare -a var 语句来指定一个数组。

数组访问:通过下标的方式访问 --- ${var[number]}。数组元素的下标由0开始,和C语言类似。下标可以是整数算术表达式,其值应大于或等于0

在数组中,${#array[*]}${#array[@]} 表示数组中元素的个数

8.1 初始化方式

shell中使用括号来表示数组,元素之间则使用 空格符号 分隔。

代码语言:txt复制
<code class="txt"># 等号两边不能空格array_name=(element_1 element_2 ... element_N)# 声明偶数arr_odd=(1 3 5 7 9)</code>
登录后复制
8.2 获取数组中的元素代码语言:txt复制
<code class="txt"># 数组名[索引] 方式$(array_name[index])# 示例echo ${arr_odd[2]}</code>
登录后复制

打印数组中所有元素

代码语言:txt复制
<code class="txt">${arr_odd[*]}  # 建议使用该方式${arr_odd[@]}  # 该方式在shellcheck中会无法认可,对</code>
登录后复制

在数组声明时添加一个额外的 declare -a语句,可加速后续的数组操作速度。

代码语言:txt复制
<code class="txt">declare -a arr_name=(...)</code>
登录后复制
8.3 删除数组元素

在shell中,使用unset命令来删除数组元素。语法格式:

代码语言:txt复制
<code class="txt"># 删除特定的元素unset array_name[index]# 删除整个数组unset array_name    # 使用数组名,不写下标</code>
登录后复制
8.4 二维数组

二维数组本质也是一维数组。通过 的寻址方式来对数组进行引用和操作。

一维数组中由单行组成,而二维数组连续的多行组成。

9. 分支与循环控制双中括号[[ ... ]] 结构 在bash中,引入 [[ ... ]] 扩展测试命令。这种方式一般直接使用数学符号判断时使用。例如代码语言:txt复制
<code class="txt">if [[ "$1" > "$2" ]];then</code>
登录后复制
双圆括号((...)) 结构 允许进行算术扩展和赋值。例如:a=$(( 5 + 3 ))。该风格类似于C语言风格中的变量操作处理方式。9.1 if和if嵌套

if/then结构用来判断命令列表的退出状态码是否为0

if单分支 语法格式:代码语言:txt复制
<code class="txt">if [ condition ];then    command1    command2    ...fi # 注意不能少了fi结尾#例如if [ "$1" -gt 18 ];then    echo "you are an adult"fi</code>
登录后复制
if多分支 语法格式:代码语言:txt复制
<code class="txt">if [ condition ];then    command1    command2    ...else    command3fi#例如if [ "$1" -gt 18 ];then    echo "you are an adult"else    echo "You are a minor and you should study hard"fi</code>
登录后复制
if嵌套 语法格式:代码语言:txt复制
<code class="txt">if [ condition1 ];then    if [ condition2 ];then        command1        ...    fifi</code>
登录后复制
9.2 for循环

语法格式:

代码语言:txt复制
<code class="txt"># [list] 是一个列表,类似list1 list2 list3 ... listNfor arg in [list];do #如果do和for在同一行,则注意中间加个分号    command1    command2    ...done</code>
登录后复制

具体实例:

代码语言:txt复制
<code class="txt"># 方式 1 for i in {1..4};do # 类似python中使用in的方式判断    echo "This is No $i"done# 方式 2for((i=1;i<=5;i++));do # 类似C语言风格来实现    echo "This is No $i"done</code>
登录后复制
9.3 while循环语句

在循环的开头判断条件是否满足,如果条件为True,则一直循环。

语法格式:

代码语言:txt复制
<code class="txt">while [ condition ];do    command1    command2    ...done</code>
登录后复制

具体实例:计算两个数字之间的和(程序很简单,是本人Test所以加了一些说明)

代码语言:txt复制
<code class="txt">echo "-------This program calculates the sum of all the numbers between two numbers-------"echo "please inpput first number (need Must be less than the second number): "read aecho "Please input second number (Must be greater than the first number): "read bsum=0while ((a <= b));do    ((sum+=a))    ((a++))doneecho "the plus is : $sum"</code>
登录后复制
9.4 until循环语句

在循环的顶部判断条件,如果condition为False,就进入循环,和while语句相反。

语法格式:

代码语言:txt复制
<code class="txt">until condition;do # 如果condition为True,直接结束循环    command1    command2    ...done</code>
登录后复制

实例:计算1~50的乘积

代码语言:txt复制
<code class="txt">#程序使用C语言风格,如果使用shellcheck是会直接报错set i=1sum=0until ((i>50));do    ((sum+=i))    ((i++))doneecho "The puls is : $sum"</code>
登录后复制
9.5 break和continue语句

直接影响循环行为的命令:breakcontinue

break 直接跳出循环continue 只跳过本次循环,忽略本次循环剩余代码,直接进入下一次循环。9.6 case结构语句

case结构语句类似C语言中的switch语句。个人使用场景:写多个dockerfile(如ubuntu16.04、ubuntu18.04、centos7.2等)则使用一个变量控制,保证会执行的命令。

语法格式:

代码语言:txt复制
<code class="txt">case arg/expression in    condition_1)        command_1    ;;    condition_2)        command_2    ;;    ......    condition_N)        command_N    ;;    *)        commandesac</code>
登录后复制

⚠️注意:

每句测试行,都以右小括号)结尾.每个判断语句块都以一对分号;; 结尾。case块以 esac(case的反向拼写) 结尾。

具体实例:打印成绩评级

代码语言:txt复制
<code class="txt">#已进行shellcheck检查echo "Please input your Score : "read -r scorecase $score in #固定格式,判断数字,然后直接类似C语言中的goto语句    [9][0-9]|100) # 十位 和个位的组合        echo "The Level is A"        ;; # 固定格式    [8][0-9]|90)        echo "The Level is B"        ;;    [67][0-9]|80)        echo "The Level is C"        ;;    [0-5][0-9]|[0-9])        echo "The Level is D, please pay attention it"        ;;    *) #固定格式        echo "The input is False"esac # 注意结尾不能少</code>
登录后复制
9.7 select结构语句

select结构语句case结构语句类似,是建立menu的一种工具

语法格式:

代码语言:txt复制
<code class="txt">select arg in [list];do    command_1    command_2    ......    break # 一定要使用break,否则会直接一直提示你选择内容,无法退出(只能通过ctrl+c方式进行)done</code>
登录后复制

提示用户输入选择的内容(比如放在变量列表中). 注意: select命令使用PS3提示符, 默认为

(#?), 可修改。

具体实例:

代码语言:txt复制
<code class="txt">#已进行shellcheck检查PS3="Please choose the OS you are using : "  #直接将提示字符串赋值给PS3变量,即可替代符号 #?select os_type in "ubuntu1604" "Ubuntu1804" "Centos8" "OpenEuler";do    echo "The OS you are using : $os_type"    breakdoneexit 0</code>
登录后复制
10. 函数

函数:实现一系列操作的代码块(完成特定task)。一个函数就是一个子程序。

目的:提高代码的重用性。

10.1 自定义函数

语法格式:

代码语言:txt复制
<code class="txt"># 方式 1 function func_name(){ # function在shell中专门定义函数    command1    command2    ...    [return value]}# 方式 2 : 简化写法function_name(){    command1    command2    ...    [return value]}</code>
登录后复制

⚠️注意:

关键字function可有可无。函数定义必须在第一次调用函数之前完成。一个函数可以嵌套另一个函数。不用在函数中指明参数,只需在调用时传递参数即可。10.2 函数的调用

在shell中,调用函数时可直接使用名字即可。如果有参数,设置即可。

代码语言:txt复制
<code class="txt">func_name [param_1] [param_2] ... [param_N]</code>
登录后复制

具体实例:

代码语言:txt复制
<code class="txt"># 最简单的例子function print_infor(){    echo "My Name is : $1"    echo "My Age is : $2"}print_infor solerho 26</code>
登录后复制
10.5 系统函数

暂时未使用到,所以不做更新。

11. 字符串的显示颜色

ANSI定义了屏幕属性相关颜色输出的转义码来表示。

一般会看到打印信息中显示特殊的颜色。通过echo带颜色属性,以及参数 -e。语法格式如下:

代码语言:txt复制
<code class="txt"># 方式 1 ---- 容易出现数字混乱echo -e "[字背景颜色;文字颜色m 字符串"# 方式 2 ---- 看起来简洁echo -e "e[字背景颜色;文字颜色m 字符串e[0m"</code>
登录后复制

说明:echo中 -e启用转义序列。其中字体或者背景等编号都会以 m 结尾

颜色

字体颜色

背景颜色

显示控制说明

30m

40m

0m ---- 关闭所有属性

31m

41m

1m ---- 设置字体高亮(也就是粗体字)

绿

32m

42m

2m ---- 设置字体变暗(也就是灰字)

33m

43m

3m ---- 设置斜体

34m

44m

4m ---- 设置字体下划线

35m

45m

5m ---- 设置字体闪烁

36m

46m

7m ---- 设置颜色反转

37m

47m

8m ---- 设置隐藏(如Linux中输入密码)

具体实例:

代码语言:txt复制
<code class="txt"># 已进行shellcheck检查echo -e " This is Black Font "echo -e " This is Red Font "echo -e " This is green Font "echo -e " This is yellow Font "echo -e " This is Blue Font "echo -e " This is Purple Font "echo -e " This is Cyan Font "echo -e " This is White Font "echo -e " This is Black background "echo -e " This is Red background "echo -e " This is green background "echo -e " This is yellow background "echo -e " This is Blue background "echo -e " This is Purple background "echo -e " This is Cyan background "echo -e " This is White background "</code>
登录后复制

打印信息如下:

一文掌握shell脚本的基本语法shell字体显示颜色.png

更多详细情况请移步 https://misc.flogisoft.com/bash/tip_colors_and_formatting

12. I/O重定向

该部分不谈基本原理和具体实现,具体可查看 csapp 和 Linux内核中fd内容分析

shell脚本(Linux中保存log等操作也是如此)中,常用的I/O重定向相关的文件描述符(file description,简写fd)有3个:

stdin ----- 标准输入 ----- 0 ----- 键盘stdout ----- 标准输出 ----- 1 ----- 屏幕stderr ----- 标准错误 ----- 2 ----- 错误消息输出到屏幕上12.1 重定向符号及功能说明

符号

描述

注意点

用法例子

:> filename 或 > filename

如果文件存在,则创建一个0长度的文件(与touch类似)

: 是一个占位符,不产生任何输出

1>filename

重定向stdout 到文件 filename中

1>>filename

如果文件存在,则直接重定向追加到文件filename后面,如果不存在,则创建。

2>filename

重定向stderr到文件filename

2>>filename

重定向并追加stderr到文件filename

&>filename

将stdout 和 stderr 都重定向到文件filename

2>&1

重定向stderr到stdout,将错误消息的输出,发送到与标准输出所指向的地方

i>&j

重定向文件描述符i到j,指向i文件的所有输出都发送到j

>&j

默认的,重定向fd 1(stdout)到j,所有传递到stdout的输出都送到j中去

0<filename filename></filename>

从文件中接受输入

grep search_word

[j] filename

将filename打开,然后将fd j分配给他,如果filename不存在,则创建。

如果fd未指定,则默认fd是0。

12.2 关闭文件描述符

该使用场景本人暂未遇到,但是看到一些code在使用。

符号

说明

n

关闭输入文件描述符n

0

关闭stdin

n>&-

关闭输出文件描述符n

1>&-,>&-

关闭stdout

12.3 代码块重定向

代码块:就是 {} 括起来的命令。例如:for循环、while循环、until循环、case语句等。

具体用法:将重定向命令符号写在代码块的结尾。具体实例:

代码语言:txt复制
<code class="txt">echo "This is Code block redirect Example"echo {    echo "SolerHO";    echo "shell";    echo "55"} > infor.log   # 将代码块重定向输出到infor.log 文件中{    read -r name;    read -r dev_lang;    read -r age} < infor.log   # 将infor.log重定向输入到代码块 echo "My Name is $name, The programming language being used is $dev_lang, age is $age"</code>
登录后复制
13. 正则表达式

正则表达式(Regular Expression,简称regex或RE):由一系列的特殊字符组成的字符串,每个特殊字符都称为 元字符(一般解释为特定的含义)。

主要目的:用于搜索文本和字符串的操作。

一般情况下,可以通过 https://tool.oschina.net/regex/ 来验证自己写的是否可以匹配预期想要的结果。

13.1 正则表达式组成

正则表达式由普通字符元字符(也称为通配符)组成的集合,用来查找匹配特定规则的字符文本。

一个正则表达式中,会包含以下一种或者三种:

一个字符集:只包含表示字面意义的普通字符。锚:指定所要匹配的文本在文件中所处的位置。如 ^$ 。修饰符:扩大或缩小匹配范围常见的修饰符:星号(*)括号反斜杠()。13.2 POSIX字符类 [:class:]

字符

描述

⚠️注意点

[:alnum:]

匹配字母和数字,等价于A-Za-z0-9

[:alpha]

匹配字母,等价于A-Za-z

[:blank:]

匹配一个空格或一个制表符(tab)

[:cntrl:]

匹配控制字符

[:digit:]

匹配十进制数字,等价于0-9

[:graph:]

打印任何可视的字符。ASCII码范围:33 ~ 126 之间的字符

不包括空格字符(空格字符的ASCII码是32)

[:print:]

打印任何可视的字符。ASCII码范围:33 ~ 126 之间的字符

包含空格

[:lower:]

匹配小写字母,等价于 a-z

[:upper:]

匹配大写字母,等价于A-Z

[:space:]

匹配空白字符(空格和水平制表符)

[:xdigit:]

匹配16进制数字,等价于 0-9A-Fa-f

POSIX字符类通常都要用引号双中括号([[ ]])引起来。

13.2 扩展RE字符

字符

描述

⚠️注意点

星号 --- *

匹配它前面字符的任意多次,包括0次

点 --- .

匹配任意一个字符,除了换行符

⚠️注意:不包含换行符

脱字符号 --- ^

匹配行首

有时候也表示字符集取反

美元符 --- $

在RE中匹配行尾

放在字符的后面,例如 HO$ --- 表示以 HO结尾的字符

中括号 --- [...]

在RE中,匹配中括号内字符集中的某一个字符

匹配其中之一

反斜杠 --- |转义某个特殊含义的字符|如 $ 符号,使用反斜杠后,则表示普通字符

问号 --- ?

匹配它前面字符

只能匹配1次或0次,一般用来匹配单个字符

加号 --- +

匹配它前面字符,一次或者多次

不能匹配0次的情况

竖线 ---

或操作符

匹配其中之一即可

转义的尖括号 --- <...></...>

匹配单词边界

括号需使用转义符,否则就是普通的字符

转义的大括号 --- {...}

括号中使用数字,则表示数字前面的RE匹配的次数

括号需使用转义符,否则就是普通的字符

13.1 应用场景代码语言:txt复制
<code class="txt">- Linux文本处理:sed、grep、awk、cat、tail、head、tee、uniq、sort- Linux工具:vim- 其他的编程语言</code>
登录后复制

详细关于正则表达式内容阅读:https://www.runoob.com/regexp/regexp-tutorial.html

14. Linux / shell中一些命令说明

更多关于Linux相关的命令,请移步目录 Linux 关注知识点笔记。

关于里面的参数选项则不做出过多解读,只增加目前使用到的,后续有使用过其他的,也会再次更新。

14.1 set/ unset命令 -- 设置/取消赋值

内容只介绍在实际生产中的情况,更多的细节请阅读:https://www.computerhope.com/unix/uset.htm

在命令中直接输入 set,则显示系统中已经存在的一些shell变量。设置新变量值代码语言:txt复制
<code class="txt">```sh</code>
登录后复制
代码语言:txt复制
<code class="txt">set var[n]=value</code>
登录后复制
代码语言:txt复制
<code class="txt">set -ex var</code>
登录后复制
代码语言:txt复制
<code class="txt">```</code>
登录后复制

参数选项

-e(errexit):如果命令的返回值不是0,则直接退出shll的执行。-x():执行命令后,优先显示该命令及对应的参数。14.2 read命令 -- 从控制台读取输入

参考:https://www.computerhope.com/unix/bash/read.htm

从屏幕标准输入中读取一行。默认情况下,read将换行符作视为行的结尾。

代码语言:txt复制
<code class="txt">read [-ers] [-a array] [-d delim] [-i text] [-n nchars] [-N nchars]     [-p prompt] [-t timeout] [-u fd] [name ...] [name2 ...]</code>
登录后复制

在while循环中使用的 -r 则是直接使用原始的输入。例如

代码语言:txt复制
<code class="txt">read -r name        # 读取控制台输入的name值read -r age         # 读取控制前台输入的age值</code>
登录后复制
14.3 declare命令 -- 声明shell变量

参考链接:https://www.computerhope.com/unix/bash/declare.htm

几个功能

声明shell变量和函数设置属性显示值

语法:

代码语言:txt复制
<code class="txt">declare [-a] [-A] [-f] [-F] [-g] [-i] [-l] [-n] [-r]        [-t] [-u] [-x] [-p] [name[=value]] [name[=value]] ...</code>
登录后复制

具体使用的例子:

代码语言:txt复制
<code class="txt"># 数组声明中使用,可加速数组的操作速度# shellcheck中也会无异常declare -a arr[]=(...)</code>
登录后复制
14.4 let命令 -- 计算算术表达式

直接参考:https://www.computerhope.com/unix/bash/let.htm

功能:主要用于计算算术表达式

let是Linux内置命令。而 ((...))是复合命令。

代码语言:txt复制
<code class="txt">let arg [arg ...]       # 和 ((...)) 直接计算算术表达式的思想类似# 示例let "var = 5";echo $var     # 直接返回 5</code>
登录后复制
14.5 expr命令 -- 表达式

通用求值表达式:通过给定的操作(参数之间必须空格隔开)连接参数,并对参数求值。可使用算术、比较、字符串或逻辑操作。

代码语言:txt复制
<code class="txt">expr 3 + 5      # 返回8expr 3 * 5     # 乘法符号需要转义,返回15</code>
登录后复制

字符串操作的请查看字符串部分。

14.6 test命令 -- 判断检查

直接参考:https://www.computerhope.com/unix/test.htm

检查文件类型并比较值。

代码语言:txt复制
<code class="txt"># 语法test expression# 应用 1:比较两个字符串(一般是判断字符串是否相等),比较运算符移步前面介绍部分 ---------> 比较运算符# 应用 2:数字大小比较</code>
登录后复制
15. Linux三剑客 --- grep

grep ---- global regular expression print,通过正则表达式来进行多用途文本搜索,属于一个过滤器。

语法格式:

代码语言:txt复制
<code class="txt">grep [OPTION]... PATTERN [FILE]...      # pattern 可以是要搜索的字符串,也可以正则表达式# 扩展命令 egrep 等价于 grep -E# 扩展命令 fgrep 等价于 grep -F</code>
登录后复制
15.1 常用查找option说明

option

全称

说明

示例

-i

--ignore-case

在搜索时忽略大小写

一文掌握shell脚本的基本语法grep忽略大小写.png

|-w|--word-regexp|强制匹配整个字符单词||

一文掌握shell脚本的基本语法grep强制匹配完整字符.png
15.2 输出控制option说明

option

全称

说明

示例

-c

--count

显示pattern匹配的次数

一文掌握shell脚本的基本语法grep输出控制计数.png

|-l|--files-with-matches|显示文件中匹配字符的文件名||

一文掌握shell脚本的基本语法grep显示存在字符的文件名.png

|-n|--line-number|打印字符匹配所在的行||

一文掌握shell脚本的基本语法grep打印pattern所在的行.png

|-o|--only-matching|仅显示匹配的字符串(可以和 -n 结合使用)||

一文掌握shell脚本的基本语法grep仅显示匹配的字符.png

|-v|--invert-match|小写,显示不匹配字符的内容||

一文掌握shell脚本的基本语法grep显示不匹配patten的字符内容.png

|-m|--max-count=NUM|显示匹配字符的某一行的内容,适合绝对匹配||

一文掌握shell脚本的基本语法grep显示匹配pattern的特定内容.png
15.3 其他两个常用RE进行的grep操作显示文件中以 "xxxx" 开头的内容,使用符号 ^ 代码语言:txt复制
<code class="txt">cat xxxx.sh | grep "^xxxx"  # 以字符xxxx开头的内容行</code>
登录后复制

示例:

一文掌握shell脚本的基本语法grep显示以pattern开头的内容.png
显示以 “xxxx” 结尾的文件名或者文件内容行,使用符号 $代码语言:txt复制
<code class="txt">cat xxxx.sh | grep "xxxx$"        # 显示以 xxxx 内容结尾的内容行</code>
登录后复制
代码语言:txt复制
<code class="txt">示例:</code>
登录后复制
一文掌握shell脚本的基本语法grep显示以pattern结尾的内容行.png
16. Linux三剑客 --- sed

sed ----- stream editor,是文本处理工具。主要是查找并替换文本字符串等。

语法:

代码语言:txt复制
<code class="txt">sed [OPTION]... {script-only-if-no-other-script} [input-file]...</code>
登录后复制

目前常用的格式为:

代码语言:txt复制
<code class="txt">sed -i 's/查找的字符串(可包含RE)/替代内容/g' filename # 如果在s/... /g 中包含单引号,则外面直接使用 双引号(""),⚠️注意中间使用一些特殊字符sed -i "s/查找的字符串(可包含RE)/替代内容/g" filename </code>
登录后复制

参数说明

i 一般是默认,可设置为其他option,具体 sed --help 查看。s 查找///分隔符,也可以是其他的字符。例如在Jenkins的pipeline语法中使用时(sed -i "s#search_word#target_word#g" filenameg 表示直接全局替换 ----- global replacement。如果是需要忽略大小写时,可使用gi

几个具体的使用场景:vim命令行模式中操作和直接操作文本是相同原理

16.1 替换/修改字符串代码语言:txt复制
<code class="txt"># 全局替换(vim亦可),且忽略大小写sed -i "s/Hello/This is/g" helloworld.sh    # 将文件helloworld.sh 中 Hello替换为 This is# 指定行替换(vim亦可),区分大小写sed "10,20 s/42m/46m/g" color_print.sh      # 将color_print.sh中10~20行之间的颜色42m替换成46m</code>
登录后复制
16.2 换行、删除代码语言:txt复制
<code class="txt">sed -i "s/ /
/g" helloworld.sh      # 将文件中空格全部换行(
)sed "///d" helloworld.sh          # 将文件中的 /所在的行直接删除(也就是#!/bin/bash)</code>
登录后复制
16.3 注释代码语言:txt复制
<code class="txt"># 全局删除sed "/^#|^$| *#/d" checkpip_deps.sh       # 将文件中注释直接全部删除</code>
登录后复制
16.4 查看指定的行范围的内容代码语言:txt复制
<code class="txt">sed -n -e "5,7p"  [-e ...] font_color.sh # 查看指定范围内的内容,可使用多个 -e来指定多个行区间sed "5,7d" font_color.sh # 查看指定范围之外的内容,可重复使用</code>
登录后复制
17. Linux三剑客 --- awk

awk ---- ,是报告可视化工具,文本格式化输出工具。主要处理文本文件。

17.1 语法格式代码语言:txt复制
<code class="txt">awk [-F 分隔符] '{ACTION}' filenamesawk [option] '{ACTION}' </code>
登录后复制
17.2 awk的原理

从第1行到最后1行,逐行去扫描文件内容,然后找到匹配pattern的行,最后进行指定的ACTION。

未指定pattern,则所有行都会被处理。未指定ACTION,则屏幕直接打印匹配到行的内容。18. shell脚本静态检查 --- shellcheck

详细内容直接阅读:https://github.com/koalaman/shellcheck,如下为使用方式:

安装方式代码语言:txt复制
<code class="txt"># 方式 1 : 直接命令行方式安装apt-get install shellcheck   # Ubuntu# centos暂时未使用 yum install ShellCheck,建议直接使用源码方式安装# 方式 2 : 源代码方式wget https://github.com/koalaman/shellcheck/releases/download/v0.8.0/shellcheck-v0.8.0.linux.x86_64.tar.xz && tar -xf shellcheck-v0.8.0.linux.x86_64.tar.xz && cp shellcheck-v0.8.0/shellcheck /usr/bin/# 查看shellcheck 版本shellcheck --version</code>
登录后复制
使用方式

直接调用shellcheck加上自己的脚本,可检测一些语法或者格式问题等。

代码语言:txt复制
<code class="txt">shellcheck testop.sh</code>
登录后复制

显示信息:

一文掌握shell脚本的基本语法shellcheck例子.png
19. 参考资源《高级bash脚本编程指南》https://juejin.cn/post/6844904045329514504https://juejin.cn/post/6962032698697187364https://myshell-note.readthedocs.io/en/latest/index.htmlhttps://github.com/koalaman/shellcheck

以上就是一文掌握shell脚本的基本语法的详细内容,更多请关注php中文网其它相关文章!

最佳 Windows 性能的顶级免费优化软件
最佳 Windows 性能的顶级免费优化软件

每个人都需要一台速度更快、更稳定的 PC。随着时间的推移,垃圾文件、旧注册表数据和不必要的后台进程会占用资源并降低性能。幸运的是,许多工具可以让 Windows 保持平稳运行。

下载
来源:php中文网
本文内容由网友自发贡献,版权归原作者所有,本站不承担相应法律责任。如您发现有涉嫌抄袭侵权的内容,请联系admin@php.cn
最新问题
开源免费商场系统广告
热门教程
更多>
最新下载
更多>
网站特效
网站源码
网站素材
前端模板
关于我们 免责申明 举报中心 意见反馈 讲师合作 广告合作 最新更新 English
php中文网:公益在线php培训,帮助PHP学习者快速成长!
关注服务号 技术交流群
PHP中文网订阅号
每天精选资源文章推送
PHP中文网APP
随时随地碎片化学习

Copyright 2014-2025 https://www.php.cn/ All Rights Reserved | php.cn | 湘ICP备2023035733号