1.shell概述

1.1什么是shell?

前言:真正能够控制计算机硬件(CPU,内存,显示器)的,只有操作系统内核(kernel),图形化界面和命令指示假设在用户和硬件之间的一层桥梁。

由于安全、复杂、繁琐等原因,用户不能直接操作内核(不能也没必要),需要有一个桥梁,让用户通过这个桥梁,能够协调硬件资源。这个桥梁的作用就是链接用户与内核,接收到用户需求(命令等),简单处理过后传递给内核。这样的话,用户和内核之间多了一层类似于“代理”的东西,这层代理既保护了内核,又方便了用户。

如果用户直接操作计算机底层硬件资源,会造成不可逆转的错误,为了保护硬件资源,现在引入shell。

用户与硬件之间的关系:

1.2shell

shell既是应用程序,又是一种程序设计语言。

作为应用程序:shell是一个解析器

作为语言:shell是一种解释型语言,不需要编译,边解释边执行(批数据处理

shell的功能:

1.自动化任务,可以完成一些重复性工作,例如定时清理日志,定时备份重要文档。

2.系统管理:可以协助用户管理系统系统资源。

3.软件安装与部署:根据shell脚本进行对应的配置,完成软件的自动化安装(后续会涉及到环境不同,环境配置也不同)

1.3shell的解析器版本

Linux中常用的shell解析器有三种:sh、ash、bash。在咱们常用的linux中,默认使用的解析器是:bash

1.4shell语言

shell是一种脚本语言,类似于C语言,我们只要按照相应的语法来进行相应的编辑,增加可执行权限,就可以在安装shell命令解释器的环境下执行。

1.5shell语言的种类

linux中的shell语言大致分为两类(进行环境配置)

1./etc/profile

针对linux下所有用户的配置(无论登录哪一个用户),用户第一次登录的时候,此配置执行

2.~/.bashrc

linux中每一个用户有一个对应的环境配置(登录用户不同,环境不同)

2.shell语法

2.1shell脚本文件

shell脚本文件是以.sh为后缀的

如果跨系统操作,例如在windows写的文件拖动到linux中,可能因为语法差异导致报错。(例如:linux中换行与windows可能不同)

解决方法:

2.2shell脚本语言的执行

方法1.chmod + x xxx.sh      然后./xxx.sh

方法2:bash xxx.sh   指定bash读取解析xxx.sh

方法3:. xxx.sh使用当前解析器读取解释xxx.sh

几种方法的区别:

1 ./与 bash执行过程基本一致:

a ./先去找#!/etc/ 指定的解析器,如果没有指定,选择默认解析器

b 后者指定用bash解析器运行,那么文件中的#!/etc/ 指定的解析器将不再起作用

c ./ 和bash都会另外开启一个解析器来解析(新开一个终端)

2  . 执行脚本不会开启新的shell,直接用当前的shell来解析

3.shell的变量

3.1定义变量

定义变量:变量=变量值

变量取值:$变量名注意:=两边不能有空格

清除变量:unset

读取变量:read

read num  #读取变量
read str #读取字符串

只读变量:readonly 

导出环境变量:(只导出当前终端,与其他无关)

先查看环境:终端输入 env

导出环境:export

可与理解为:

3.2双引号和单引号的区别

单引号:将单引号引起来的内容原封不动输出

双引号:可以将其中的变量解析

3.3系统预设变量(env中的)

3.4 $预设环境变量

$#:传给 shell 脚本参数的数量
$*:传给 shell 脚本参数的内容
$1、$2、$3、...、$9:运行脚本时传递给其的参数,用空格隔开
$?:命令执行后返回的状态
"$?"用于检查上一个命令执行是否正确(在 Linux 中,命令退出状态为 0 表示该命令正确执行,任何非 0 值表示命令出错)。
$0:当前执行的进程名
$$:当前进程的进程号
"$$"变量最常见的用途是用作临时文件的名字以保证临时文件不会重复

3.5脚本变量的特殊用法

  • ``(数字1左边的)反引号,反引号中的内容作为系统命令,并且执行其内容,进行替换输出

  • 转义字符 \  等同于C语言中转义字符  \r   \n  \a等,但是需要加上 -e才能生效

  • ()内的命令序列,只会影响()内的数据
  • {}内的命令序列,会影响整个shell文件的数据

3.6条件测试语句

在写shell脚本时,经常遇到的问题就是判断字符串是否相等,可能还要检查文件状态或者进行一些数字测试,那么只有完成测试以后才能进行下一步动作

  • test 命令可以完成 字符串、文件状态和数字测试
    • 格式1:test condition
    • 格式2: [ condition ]  注意,condition左右各有一个空格

3.6.1文本测试

判断条件:

-e 是否存在

-d 是目录

-f 是文件
-r 可读

-w 可写

-x 可执行
-L 符号连接

-c 是否字符设备

-b 是否块设备
-s 文件非空

3.6.2字符串测试

测试格式

格式1:

  • test str_operator  "str"   (测试目标为1个)
  • test "str1"  str_operator  "str2"  (测试目标为2个)

格式2:

  • [ str_operator  "str" ](测试目标为1个)
  • [ "str1"  str_operator  "str2" ](测试目标为2个)([ ]左边右边各有一个空格)

其中 str_operator 可以是:
= 两个字符串相等

!= 两个字符串不相等
-z 空串

-n 非空串

3.6.3数值测试

测试格式:

格式1

  • test num1 num_operator num2
  • [ num1 num_operator num2 ]

num_operator 可以是如下

3.6.4复合测试

4.控制语句

if   case   for   while   until   break

4.1.if语句

4.1.1 if else语句

格式1:

if [ 条件 ];then  #条件左右要加空格   
    语句1    #如果满足if后,执行此处
else
    语句2   #否则执行此处
fi    #结束

代码案例:

代码案例:

输入一个文件名,判断是否存在,如果存在,展示内容,如果不存在,创建文件并且输入内容

#!/bin/bash
echo "请输入一个文件名"
read filename
if [ -e $filename ];then
    if [ -d $filename -o -s $filename ];then
    echo "为目录文件或文件为空"
    else
        cat $filename
    fi
else
    touch $filename
    echo "hello file" >> $filename
    cat $filename
fi

格式2:

if [ 条件1 ];then
    语句1
elif [ 语句2 ];then
    语句2
else
    语句3
if

4.2case

格式:

case $变量名称 in
    "值1")
    程序段一
        ;;
    "值2")
    程序段二
        ;;
     *)    #其他情况
    其它程序段
exit 1  #退出
esac   #结束 case倒过来写

代码案例:

#!/bin/bash
echo "请输入一个选择"
read str
case $str in
    y*|Y*)  #输入y开头或者Y开头的选择都会匹配  通配符
    echo "用户输入确定"
    ;;
    "no")
    echo "用户选择退出"
    ;;
    *)
    echo "用户无操作"
    exti 1  #退出
esac



4.3for

格式1:

for((初始值;限制值;执行步阶)) # for((i=0;i<=10;i++))
do
    程序段;
done

案例:计算1+2+。。。+10

#!/bin/bash
declare -i i=0   #declare -i xx  将xx强制当成int类型数据来计算
declare -i data=10
declare -i sum=0
for((i;i<=data;i++))
do
sum=$sum+$i
done
echo "sum=$sum"  #结果为55

格式2:

for var in con1 co2 con3 ...    
do
    程序段
done
第一次循环时,$var 的内容为 con1
第二次循环时,$var 的内容为 con2
第三次循环时,$var 的内容为 con3

代码案例:

#!/bin/bash
declare -i i=0   #declare -i xx  将xx强制当成int类型数据来计算
declare -i data=10
declare -i sum=0
for var  in 1 2 3 4 5 6 7 8 9 10
do
sum=$sum+$var
done
echo "sum=$sum"  #结果为55

4.4while循环

格式:

while [ 条件 ]
do
    代码段
done

代码案例

#!/bin/bash
declare -i i=0   #declare -i xx  将xx强制当成int类型数据来计算
declare -i data=10
declare -i sum=0

while [ $i -le 100 ]
do
    sum=$sum+$i
    i=$i+1
done
echo "sum=$sum" #结果为5050


4.5until

格式:

until [ 条件 ]
do
    代码段
done
#until用法与while恰好相反,until是condition成立时退出循环

代码案例:

#!/bin/bash
declare -i i=0   #declare -i xx  将xx强制当成int类型数据来计算
declare -i data=0
declare -i sum=0

until [ $i -gt 100 ]
do
    sum=$sum+$i
    i=$i+1
done
echo "sum=$sum"

5.函数

可以解决脚本语言的重复性调用问题

格式1:

函数名(){
命令...
}

格式2:推荐

function 函数名(){    #shell脚本无需形参
命令...
}

5.1.当前源文件封装函数

案例:

#!/bin/bash
declare -i i=0   #declare -i xx  将xx强制当成int类型数据来计算
declare -i data=0
declare -i sum=0

#函数定义
function my_add() 
{
    sum=$1+$2
    return $sum
}

#函数传参
my_add 10 20  #10会代替$1  20会代替$2

#函数结果,上一行命令执行的结果
echo "结果是:$?" #结果是30   

5.2函数分源文件(函数在别的文件)

需要导入

#!/bin/bash
source xxx #用source导入my_add函数所在的文件


#函数传参
my_add 10 20

#函数结果,上一行命令执行的结果
echo "结果是:$?"

Logo

openvela 操作系统专为 AIoT 领域量身定制,以轻量化、标准兼容、安全性和高度可扩展性为核心特点。openvela 以其卓越的技术优势,已成为众多物联网设备和 AI 硬件的技术首选,涵盖了智能手表、运动手环、智能音箱、耳机、智能家居设备以及机器人等多个领域。

更多推荐