Linux - Shell - 基础语法
Linux Shell 基础语法
脚本
标记
#!/bin/bash是shell脚本的第一行代码,表示该脚本使用什么解释器;
#!/bin/bash
echo命令用于向窗口输出文本;
echo "hello shell"; # 开启转义 换行 echo -e "hello \n shell"; # 反引号 显示命令执行结果 echo `ls /`; # 将显示结果定向到文件 echo 'hello' > 1.txt;
单行注释
# 表示单行注释;
多行注释,EOF还可以用其他符号,例如!
:>>EOF 注释内容1 注释内容2 EOF :>>! 注释内容1 注释内容2 !
例子
创建脚本文件,命名为/tmp/hello.sh
#!/bin/bash echo "hello shell";
赋予脚本执行的权限,执行脚本
chmod u+x /tmp/hello.sh; ./tmp/hello.sh
变量
定义使用
格式:key=value;
value当为单引号或双引号内容时,即为字符串;当为数字时,即为数值型;
使用变量用美元符号$引用,标准格式是:${key};但有时也可以使用$key;进行引用;
# 字符串变量 a='A'; b="${a}\\B"; # 只读变量 readonly c=7; # 全局变量 export d=3.14; # 单引号的内容会原样输出,不能出现单引号,不能使用转义字符 echo $a; # 双引号内容可以包含变量,可以使用转义字符 echo $b; # 删除变量 unset c;
字符串
n="0123456789"; m="aaabbbaaabbb"; # 返回字符串变量n的长度 echo ${#n}; # 返回从第5个字符开始到最后的部分 echo ${n:5}; # 返回从第0个字符开始,长度为5的部分 echo ${n:0:5}; # 删除开头部分与012匹配的部分 echo ${n#012}; # 删除结尾部分与789匹配的部分 echo ${n%789}; # 替换第一次出现的aaa为xxx echo ${m/aaa/xxx}; # 替换全部aaa为xxx echo ${m//aaa/xxx}; # 替换开头部分的aaa为xxx echo ${m/#aaa/xxx}; # 替换结尾部分的bbb为xxx echo ${m/%aaa/xxx};
执行输出:
10 56789 01234 3456789 0123456 xxxbbbaaabbb xxxbbbxxxbbb xxxbbbaaabbb aaabbbaaabbb
替换扩展
v=V; echo $v; # 若v未定义或为空值,则返回vvv,但v的值不变;若v存在且非空,则返回V; echo ${v:-vvv}; # 若v未定义或为空值,则返回vvv,且v的值被赋值为vvv;若v存在且非空,则返回V; echo ${v:=vvv}; # 若v未定义或为空值,则返回vvv,并终止脚本;若v存在且非空,则返回V; echo ${v:?vvv}; # 若v未定义或为空值,则返回空值,但v的值不变;若v存在且非空,则返回vvv; echo ${v:+vvv};
数值运算
四则运算符:+、-、*、/
幂运算符、模运算符:**、%
自增自减运算符:++、--
赋值运算符:=、+=、-=、*=、/=、%=
比较运算符:<、>、<=、>=、==、!=
逻辑运算符:&&、||、!
# 运算表达式必须在双括号内((表达式)) echo $((a=3**2));# 输出9
变量输入
格式:read -p <Prompt String> [<变量名>...];
# 输入单个变量 read -p "请输入:" n; echo $n; # 输入多个变量 read -p "请输入:" n1 n2 n3; echo $n1 / $n2 / $n3;
返回值
每个命令都会返回一个状态码,0表示成功,其他非零数值表示各种情况的错误,exit n;(n的范围是0~255),1表示通用错误,126表示没有执行权限,127表示命令没有找到;
参数
传参
格式:./shell脚本文件 参数1 参数2 ...
# 向脚本文件test.sh参入3个参数 ./shell/test.sh p1 p2 p3; # test.sh文件内获取参数 echo $1 $2 $3;
获参
# 传递到脚本的参数个数 echo $#; # 显示所有参数 echo $*; echo $@; # 显示第1个参数 echo $1; # 显示第10个参数,第10个参数起必须使用${n} echo ${10}; # 显示最后命令的退出状态,0表示没有错误,其他值表示有错; echo $?; # 当前进程的PID echo $$;
测试表达式
测试语句
格式1:test <测试表达式>
格式2:[ <测试表达式> ]
格式3:[[ <测试表达式> ]]
格式1和格式2等价,格式3可以使用&&、||、!的逻辑连接符;
格式2和3符号前后必须留空格;
a=1.1; b=1.1; if test $a == $b; then # if (( $a == $b )); then # if [ $a -eq $b ]; then # if [[ $a == $b ]]; then echo '相等'; fi;
字符串测试
-z str 字符串是否为空串;
-n str 字符串是否为非空串;
str1 == str2 两个字符串是否相同;
str1 != str2 两个字符串是否不同;
整数二元比较
[] 中使用-eq、-ne、-gt、-ge、-lt、-le;
(())中使用==、!=、>、>=、<、<=;
[]中使用-a、-o、!;
[[]]中使用&&、||、!;
文件目录测试
-e file 文件是否存在;
-f file 是否普通文件;
-d file 是否目录;
-L file 是否链接文件;
-b file 是否为块设备文件;
-c file 是否为字符设备文件;
-s file 是否长度不为零、非空文件;
-r file 是否为可读文件;
-w file 是否为可写文件;
-x file 是否为可执行文件;
-O file 是否为文件的属主;
-G file 是否为文件的属组;
-u file 是否设置了SUID的权限;
-g file 是否设置了SGID的权限;
# 当目录不存在时创建该目录 [ !-e /shell ] && mkdir -p /shell;
数组
定义
格式1:array=(a1 'a2' a3);
格式2:array[0]=a1;array[1]='a2';array[2]=a3;
# 定义数组 array=(1 '2'); # 设置第三个元素 array[2]=3; # 显示第一个元素 echo array[0]; # 获取数组的全部元素 echo ${array[*]}; echo ${array[@]}; # 获取数组的大小 echo ${#array[*]};
函数
定义
格式:function fun() { }
function关键字可以省略;
可以添加返回 return n;(n必须是0~255)执行函数后,可以通过$?获取返回值;
fun() { return 1; echo 'over'; } fun; echo $?;
流程控制
if 语句
if test -e /shell/1; then echo '1文件存在'; elif test -e /shell/2; then echo '2文件存在'; # else分支是最后的默认分支,可以省略,最多只能一个 else echo '都不存在'; fi;
case 语句
read -p '请输入:' num; case $num in 1) echo 'num=1' ;; 2) echo 'num=2' ;; *) echo 'num=?' ;; esac
while 语句
break:跳出循环;
continue:跳过本次循环,进入下一次迭代;
exit n:会中止当前函数以及调用它的主shell;
i=0; len=10; while (($i < $len));do echo $i; let "i++"; done; # 循环读取文件行内容 while read line; do echo $line; done < /shell/proxy; # 或 cat /shell/proxy | while read line; do echo $line; done;
until 语句
until 表达式与while相反,当返回值为0时结束循环;
for 语句
# 字面常量列表 for loop in 1 2 3 4 5; do echo "The value is: $loop" done; # 参数列表,in $@可以省略 for p in $@; do echo $p; done; # 序列列表 for x in {1..9}; do echo $x; done; # C语言型for循环 for((i=0;i<10;i++)) { echo $i; }
select 语句
select是一种菜单循环结构,无限循环,退出可以加入break或按<Ctrl+C>,一般加入case语句处理;
select x in 1 2 3; do case $x in 1) echo 'x=1' ;; *) echo 'x=?' ;; esac; done;
无限循环
while : # 或 while true do echo 'loop'; done; for(( ; ; )){ echo 'loop'; }