Shell 基础语法介绍

Shell 介绍

1. 定义变量的时候,"=" 两侧不能有空格
2. if 时的方括号内,"=""==" 两侧必须要有空格,且表达式和方括号也要保持空格
3. $(Linux命令) 或者 `Linux 命令` 用来执行 Linux 命令,并得到命令执行后的结果
4. if 的判断条件要写在 []5. ((表达式)) 用作 if 语句的判断条件时,不加 $ ,用在其它地方需要加 $
6. 算数运算可以使用 `expr $a + $b`

什么是 Shell

它类似于 DOS 下的 command 和后来的 cmd.exeShell 既是一种命令语言,又是一种程序设计语言

Shell 是一个用 C 语言编写的程序,通过 Shell 用户可以访问操作系统内核服务

什么是 Shell Script

Shell 编程跟 java、php 编程一样,是一个编程语言,需要一个能编写代码的文本编辑器和一个能解释执行的脚本解释器

1. Shell Script 是一种为 shell 编写的脚本程序
2. Shell 编程一般指 shell 脚本编程,不是指开发 shell 自身

shell 脚本的规范

#! 是一个标记,除了第一行的 # ,其它行的 # 表示注释

1. 编辑脚本的时候,需要在 shell 脚本中第一行的进行标记
2. 该标记用来告诉系统这个脚本需要什么解释器来执行
#!/bin/bash 

Shell 解释器

查看 Shell 解释器

Shell 解释器可以解析我们编写的脚本,注意:大多数 Linux 系统默认的 Shell 是 Bash

# 查看系统中的 Shell 解释器
cat /etc/shells

常见 Shell 解释器

注意:Linux 上,sh 已经被 bash 代替,/bin/sh 往往是指向 /bin/bash 的符号链接

① sh(Bourne shell)

1. 由 AT&T 公司的 Steve Bourne 开发,为了纪念他,就用他的名字命名了
2. sh 是 UNIX 上的标准 shell,很多 UNIX 版本都配有 sh
3. sh 是第一个流行的 Shell

② Bash

1. Bash 是 sh 的升级版本,是著名的开源软件项目
2. 目前大多数的 Linux 版本都使用 Bash 作为默认的 Shell 程序
3. 当运行 Shell 程序时,实际运行的是 Bash 程序

③ Csh

1. 使用了 C 语言的语法风格,在用户的命令行交互界面上进行了很多改进,并增加了历史,别名,文件名替换,作业掏等功能
2. Csh 适用于用户命令交互操作

Shell 脚本的执行方式

Shell 有 3 种执行方式

① sh 执行

进入脚本的工作目录,然后使用对应的 shbash 来执行脚本,这种执行方式,脚本文件不需要具有可执行权限

# 执行 start.sh
sh start.sh

② 工作目录执行

执行脚本时,先进入到脚本所在的目录,然后使用 ./ 脚本方式执行,这种执行方式,必须保证脚本文件具有可执行权限

# 在当前目录执行脚本
./start.sh

③ 绝对路径执行

绝对路径中执行,这种执行方式,必须保证脚本文件具有可执行权限

# 执行脚本
/opt/server/start.sh 

数据类型

① 字符串

字符串是 shell 编程中最常用最有用的数据类型,字符串可以用单引号,也可以用双引号,也可以不用引号

建议使用双引号,因为双引号里可以有变量和特殊字符,可以按照变量和特殊字符去使用

② 整数型

在 Shell 中所有的变量默认都是字符串型。默认情况下,所有的数值都是不能进行运算的


Shell 变量

变量介绍

Shell 变量是一种很 的变量,默认情况下,一个变量保存一个字符串

若要进行数学运算,必须使用一些命令,例如:let、declare、expr、双括号等

变量的种类

① 用户变量(使用较多)

② 环境变量(程序运行时设置)

③ 特殊变量(对参数判断和命令返回值判断时会使用)

变量的定义规则

变量名=变量值

① 变量名可以由字母、数字和下画线组成,但是不能以数字开头

② 在 Bash 中,变量的默认类型都是字符串型,如果要进行数值运算,则必须使用特殊命令

③ 变量用等号 = 连接值,= 左右两侧不能有空格

变量值中如果有空格,则需要使用单引号或双引号包含,双引号括起 来的内容 $反引号 者都拥有特殊含义,而单引号括起来的内容都是普通字符

# 示例
name="kyle white"

⑤ 在变量值中,可以使用转义符

⑥ 不能使用 bash 里的关键字


用户变量

定义变量

对变量赋于字符串值时,建议使用引号将其包裹。如果字符串中存在空格,一定要使用单引号或双引号将整个内容包裹

注意::单引号里的内容原封不动的输出,双引号里有变量的调用则会调用变量

name=kyle

访问变量

# 第一种方式
"$变量"

# 第二种方式
${变量}

在这里插入图片描述
定义脚本

#!/bin/bash
name="kyle"
age=23
echo "name=${name},age=${age}"

在这里插入图片描述
变量交互式赋值

1. 可以使用 read 关键字从键盘获取内容赋值给变量
2. 可以通过 $(linux命令) 或者 linux 命令来执行 linux 命令,并将命令的执行结果赋值给变量
#!/bin/bash
echo "welcome!"
echo "please enter your name?" 
read name
hostname_string=$(hostname)
date_string=`date`
echo "hello, $name"
echo "$date_string $hostname_string"

在这里插入图片描述
定义只读变量

使用 readonly 定义变量

#!/bin/bash
echo "welcome!"
echo "please enter your name?" 
read name
readonly name
name=root
echo "$name"

在这里插入图片描述
删除变量

使用 unset 命令可以删除变量

#!/bin/bash
name=root
unset name
echo "$name"

在这里插入图片描述


环境变量

环境变量说明

当 shell 程序启动时,都自动设置一组变量,这组变量就是环境变量

shell 中的所有命令都可以使用这些变量,环境变量可以在 /etc/profile 中设置,环境变量的名字习惯上使用大写字母

查看环境变量

# 查看所有的环境变量
env

# 查看 JAVA_HOME 的环境变量
echo $JAVA_HOME

设置环境变量

# 编辑环境变量配置文件
vim /etc/profile

# 增加环境变量
export KYLE_HOME=blog.csdn.net

# 刷新环境变量
source /etc/profile

特殊变量

特殊变量说明

在执行 Shell 脚本时,向脚本传递参数,这时候可以使用特殊变量来获取参数
Shell 常用的特殊变量如下

变量解释
$#命令行参数的个数
$n$1 表示第一个参数,$2 表示第二个参数,以此类推
$0当前程序的名称
$?前一个命令或许或函数的返回码
$*参数1 参数2 ... 形式保存所有参数
$@“参数1”“参数2” 形式保存所有参数
$$本程序的(进程ID号)PID
$!上一个命令的PID

获取执行参数

#!/bin/bash 
echo "Shell Param Test"
echo "shll_name:$0"
echo "param2:$1"
echo "param3:$2"
echo "param4:$3"
echo "parm_count:$#"
echo "$*"

在这里插入图片描述
$*$@ 的区别

# 相同点
都是引用所有参数

# 不同点
只有在双引号中体现出来,假设在脚本运行时写了三个参数 1、2、3
"*" 等价于 "1 2 3"(传递了 1 个参数)
"@" 等价于 "1" "2" "3"(传递了 3 个参数)

字符串

字符串中的单引号

单引号里的任何字符都会原样输出

单引号字符串中的变量是无效的,单引号字串中不能出现单独一个的单引号(对单引号使用转义符后也不行),但可成对出现,作为字符串拼接使用

#!/bin/bash 
name="kyle"
echo 'my name is $name'

在这里插入图片描述


字符串中的双引号

1. 双引号里可以有变量
2. 双引号里可以出现转义字符

字符串拼接

① 双引号拼接

#!/bin/bash
name="kyle"
age=23
str1="name=$name"
str2="age=$age"
echo $str1 $str2

在这里插入图片描述

② 单引号拼接

#!/bin/bash
name="kyle"
age=23
str1='name=$name'
str2='age=$age'
echo $str1 $str2

在这里插入图片描述
③ 转译原样输出

#!/bin/bash
name="kyle"
age=23
str1="name=$name"
str2="age=$age"
str3="hello,\$$name\$ "
echo $str1 $str2 $str3

在这里插入图片描述


获取字符串长度

#!/bin/bash
name="kyle"
echo "${#name}"

在这里插入图片描述


截取字符串

从第 2 个字符开始,截取 2 个字符

#!/bin/bash
str="Hello Shell"
echo "${str:2:2}"

在这里插入图片描述


查找字符串

查找字符串 pa返回第一次出现的索引

#!/bin/bash
str="spark is spark"
echo `expr index "$str" pa` 

在这里插入图片描述


算数运算符

运算说明

Shell 支持包括:算术、关系、布尔、字符串等运算符,简单的数学运算可以通过 expr 实现

注意: expr 是一款表达式计算工具,使用它能完成表达式的求值操作

1. 表达式和运算符之间要有空格,例如 1+1 是不对的,必须写成 1 + 1
2. 条件表达式要放在方括号之间,并且要有空格,例如: [a==b] 是错误的,必须写成 [ a == b ]

① 通过 $((运算表达式)) 计算

# 有没有空格都可以
a=5
b=10
echo $((a+b))

在这里插入图片描述

② 通过 expr 表达式计算

# 必须要有空格
a=5
b=10
echo `expr $a + $b`

在这里插入图片描述

③ 通过 $[运算表达式] 计算

# 有没有空格都可以
a=5
b=10
echo $[a+b]

在这里插入图片描述

常用运算符

运算符说明举例
+加法expr $a + $b 结果为 30。
-减法expr $a - $b 结果为 -10。
*乘法expr $a \* $b 结果为 200。
/除法expr $b / $a 结果为 2。
%取余expr $b % $a 结果为 0。
=赋值a=$b 将把变量 b 的值赋给 a。
==相等。用于比较两个数字,相同则返回 true。[ a == b ] 返回 false。
!=不相等。用于比较两个数字,不相同则返回 true。[ a != b ] 返回 true。

运算示例

#!/bin/bash 
a=5
b=10
# 加法运算 
each `expr $a + $b`
# 减法运算 
echo `expr $a - $b` 
# 乘法运算,注意*号前面需要反斜杠 
echo `expr $a \* $b` 
# 除法运算
echo $a / $b 
# 还可以通过$(())、$[]进行算术运算
echo "a = $a" 
echo $((a+b)) 
echo $[a+b] 

流程控制

if 语句

常用的关系运算符

① 数字判断

运算符说明
-eq检测两个数是否相等,相等返回 true
-ne检测两个数是否不相等,不相等返回 true
-gt检测左边的数是否大于右边的,如果是,则返回 true
-lt检测左边的数是否小于右边的,如果是,则返回 true
-ge检测左边的数是否大于等于右边的,如果是,则返回 true
-le检测左边的数是否小于等于右边的,如果是,则返回 true

② 字符串判断

判断符说明
-n STRING字符串长度不为零
-z STRING字符串长度为0
=判断两个字符串是否一样
!=判断两个字符串是否不一样

③ 文件判断

判断符说明
-f存在且是普通文件
-d存在且是目录
-h存在且是符号链接
-e文件存在
–r文件存在并且可读
–w文件存在并且可写
–x文件存在并且可执行

判断条件使用

① 使用关系运算符

# 方括号和运算表达式之间必须要有空格
if [ $a -eq $b ]

② 使用算数运算符

# 运算符两侧有没有空格都行
# 第一种
if (($a == $b))

# 第二种
if ((a == b))

if 语法

注意:中括号需要和表达式左右留一个空格,示例:if [ a -gt b ] ,否则会报错

# 语法格式
if condition
then
    command1 
    command2
    ...
    commandN 
fi

示例一:判断系统当前是否有多个 ssh 进程

#!/bin/bash
if [ $(ps -ef | grep -c "ssh") -gt 1 ]
then
    echo true
fi

示例二:判断指定目录是否存在,不存在则创建目录

#!/bin/bash
dir="/opt/log"
if [ ! -d $dir ]
then
    mkdir -p $dir
fi

if else语法

if condition
then
    command1
    command2
    ...
    commandN
else
    command
fi

示例一:判断是否为管理员登入

#!/bin/bash
echo "please enter your name"
username read
if [ "root"=$username ]
then
    echo "welcome,Manager"
else
    echo "welcome,Tourist"
fi

示例二:if else 结合 test 命令使用

说明:test 命令可以做各种测试并在测试成功或失败时返回它的退出状态码(为0表示为真,为1表示为假)

#!/bin/bash
num1=$((2*4))
num2=$((1+2))
# test $num1 -eq $num2
if test $[num1] -eq $[num2]
then
    echo "num1 = num2"
else
    echo "num1 != num2"
fi

if else-if else

if condition1
then
    command1
elif condition2 
then 
    command2
else
    commandN
fi

案例一:计算学生的成绩范围

#!/bin/bash
read -p "please enter your score:  " score
if [ $score -ge 90 ] && [ $score -le 100 ]; then
    echo "your grade is A"
elif [ $score -ge 60 ] && [ $score -lt 90 ]; then
    echo "your grade is B"
elif [ $score -ge 0 ] && [ $score -lt 60 ]; then
    echo "your grade is C"
else 
    echo "your inpur is wrong"
fi

案例二:使用 (()) 符号

#!/bin/bash
read -p "please enter your score:  " score
if (($score >= 90)) && (($score <= 100)); then
    echo "your grade is A"
elif (($score >= 60)) && (($score < 90)); then
    echo "your grade is B"
elif (($score > 0)) && (($score < 60)); then
    echo "your grade is C"
else 
    echo "your input is wrong"
fi

for 循环

字符型循环

1. 当变量值在列表里,for循环即执行一次所有命令,使用变量名获取列表中的当前取值
2. 命令可为任何有效的 shell 命令和语句
3. in 列表可以包含替换、字符串和文件名
4. in 列表是可选的,如果不用它,for 循环使用命令行的位置参数
# 格式
for 变量 in 值1 值2 值3…
do
程序
done

案例一:打印 in 列表

#!/bin/bash
for value in aa bb cc dd
do
  echo "value is: $value"
done

案例二:打印字符串

#!/bin/bash
for str in "I am who I am"
do
    echo $str
done

在这里插入图片描述
案例三:遍历命令执行结果

#!/bin/bash
for file in $(ls -a /opt)
do
    echo $file
done

在这里插入图片描述


数字型循环

for ((初始值;循环控制条件;变量变化)do
程序
done

案例一:1-100 的累加值

#!/bin/bash
sum=0
for ((i=0; i<=100; i= i+1))
do
  # sum=(($sum+$i))
  sum=$((sum+i))
done

echo "sum is : $sum"

在这里插入图片描述


while 循环
while 条件
do
    程序
done

案例一:1-100 的累加值

#!/bin/bash
sum=0
i=0
while ((i<=100))
do
  sum=$((sum+i))
  i=$((i+1))
done

echo "sum is : $sum"

案例二:使用 let 简洁代码

注意:let 可以实现变量前不加 $ 的计算,同时可以实现计算表达式的简写

#!/bin/bash
sum=0
i=0
while ((i<=100))
do
 let sum+=i
 let i++
done

echo "sum is : $sum"

死循环

① 第一种写法

while :
do
    command
done

② 第二种写法

while true
do
    command
done

③ 第三种写法

for (( ; ; ))

case 语句

shell case 语句为多选择语句,可以用 case 语句匹配一个值与一个模式,如果匹配成功,执行相匹配的命令

注意:case 语句也可以使用循环控制语句

# 使用注意
1. 取值后面必须为单词 in,每一模式必须以右括号结束
2. 取值可以为变量或常数
3. 匹配发现取值符合某一模式后,其间所有命令开始执行直至 ;;
4. 如果无一匹配模式,使用星号 * 捕获该值,再执行后面的命令
casein
模式1)
    command1
    command2
    ...
    commandN
    ;;
模式2)
    command1
    command2
    ...
    commandN
    ;;
esac

案例一:根据输入的值返回今天是星期几

#!/bin/bash

read -p"请输入 1 - 7 之间的数字 : " input

case $input in
   1) echo "Today is Monday"
   ;;
   2) echo "Today is Tuesday"
   ;;
   3) echo "Today is Wednesday"
   ;;
   4) echo "Today is Thursday"
   ;;
   5) echo "Today is Friday"
   ;;
   6) echo "Today is Saturday"
   ;;
   7) echo "Today is Sunday"
   ;;
   *) echo "Wrong input,check your input"
   ;;
esac

在这里插入图片描述


循环控制

continue 跳出本次循环,然后继续执行下次循环

案例:只输出 1-10 内的偶数,遇到奇数则使用 continue 跳过本次循环

#!/bin/bash
for((i=1;i<=10;i=i+1))
do
  if [ `expr $i % 2 ` != 0 ]; then
    continue
  fi
  
echo "当前的数为: $i"

done  

在这里插入图片描述
break 中断循环

案例:当遇到 5 的时候,中断当前的循环,后面的循环不会执行

#!/bin/bash
for((i=1;i<=10;i=i+1))
do
  if [ $i == 5 ]; then
    break
  fi
  
echo "当前的数为: $i"

done  

在这里插入图片描述


select 语句

select 表达式是 bash 的一种扩展应用,擅长于交互式场合,用户可以从一组不同的值中进行选择

注意:select 是个无限循环,因此要记住用 break 命令退出循环,或用 exit 命令终止脚本

select var in ... ;
do
 commond
done
.... now $var can be used ...

案例一:选择最喜欢的城市

#!/bin/bash
 
echo "which is your favorite city ? "
PS3="please enter your choice:"
select var in "Beijing" "Shanghai" "Shenzhen" "Hangzhou"
do
  break;
done
echo "You have selected $var"

函数

定义函数

用户可以自定义函数,然后在 shell 脚本中可以随便调用,定义格式如下:

注意:函数的返回值必须是整数,如果是字符串会报错

# 1. 可以带 function fun() 定义,也可以直接 fun() 定义,不带任何参数
# 2. 参数返回,可以显示加 return 返回;如果不加,将以最后一条命令运行结果,作为返回值
# 3. 所有函数在使用前必须定义。这意味着必须将函数放在脚本开始部分,直至 shell 解释器首次发现它时,才可以使用。调用函数仅使用其函数名即可

[ function ] funname()
{
    action;
    [return int;]
}

案例一:定义一个没有返回值的函数,打印欢迎语句

#!/bin/bash
print()
{
  echo "Welcome to Shell World,${USER}"
}

print

案例二:获取函数的执行结果

说明:函数返回值在调用该函数后通过 $? 来获得

#!/bin/bash
sum()
{
  read -p "请输入第一个数: " a
  read -p "请输入第二个数: " b
  
  return $(( a + b ))
}

echo "两个数的和为 $? "

在这里插入图片描述

案例三:定义一个方法,获取指定文件夹的大小

#!/bin/bash

# 定义函数
getDirSize()
{
   array=($(du -sh /opt/server))
   size=${array[0]}
}

# 调用函数
getDirSize

echo  "文件夹的大小为:$size"

在这里插入图片描述

函数参数

在 Shell 中,调用函数时可以向其传递参数,在函数体内部,可以获取参数的值

注意:不能使用 $ 获取 10 及以后的参数,需要使用 ${} 来获取

#!/bin/bash
parmFunc(){
    echo "参数 1 : $1"
    echo "参数 2 : $2"
    echo "参数 10 : $10"
    echo "参数 10 : ${10}"
    echo "参数 11 : ${11}"
    echo "参数数量: $#"
    echo "字符串输出参数: $*"
}

parmFunc 1 2 3 4 5 6 7 8 9 11 12

在这里插入图片描述


数组

数组说明

Bash Shell 只支持一维数组(不支持多维数组),初始化时不需要定义数组大小

注意:不能使用 $ 获取 10 及以后的参数,需要使用 ${} 来获取

1. 数组元素的下标由 0 开始
2. 元素用"空格"符号分割开
3. 数组中可以存放多个值

# 格式
array_name=(value1 ... valuen)

# 示例
my_array=("a" 1 2 "jack")

获取数组元素

# 格式
${array_name[index]}
#!/bin/bash
my_array=("a" 1 2 "jack")

echo "元素 1 : ${my_array[0]}"
echo "元素 2 : ${my_array[1]}"
echo "元素 3 : ${my_array[2]}"
echo "元素 4 : ${my_array[3]}"

在这里插入图片描述

获取数组所有元素

#!/bin/bash
my_array=("a" 1 2 "jack")

echo "数组所有元素 : ${my_array[*]}"
echo "数组所有元素 : ${my_array[@]}"

获取数组长度

#!/bin/bash
my_array=("a" 1 2 "jack")

echo "数组所有元素 : ${#my_array[*]}"
echo "数组所有元素 : ${#my_array[@]}"

遍历数组

① 第一种遍历方式

#!/bin/bash
my_array=("a" 1 2 "jack")

for ele in ${my_array[*]}
do 
  echo $ele
done

② 第二种遍历方式

#!/bin/bash
my_array=("a" 1 2 "jack")

for((i=0;i<=${#my_array[@]};i=i+1))
do
  echo ${my_array[$i]}
done

在这里插入图片描述


  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值