Shell语法(脚本进度条)

来源:互联网 发布:网速限制软件 编辑:程序博客网 时间:2024/06/07 17:21

逻辑判断[ ]

测试命令 作用 [ -d DIR ] 如果DIR存在并且是⼀一个⽬目录则为真 [ -f FILE ] 如果FILE存在且是⼀一个普通⽂文件则为真 [ -z STRING ] 如果STRING的长度为零则为真 [ -n STRING ] 如果STRING的长度⾮非零则为真 [ STRING1 = STRING2 ] 如果两个字符串相同则为真 [ STRING1 != STRING2 ] 如果字符串不相同则为真
  1. 大小比较
    [ ARG1 OP ARG2 ] : ARG1和ARG2应该是整数或者取值为整数的变量,OP是-eq(等于)- ne(不等于)-lt(小于)-le(小于等于)-gt(大于)-ge(大于等于)之中的一个
  2. 逻辑与或非
    带与、或、⾮非的测试命令
    [ ! EXPR ]: EXPR可以是上表中的任意一种测试条件,!表示逻辑-
    [ EXPR1 -a EXPR2 ]: EXPR1和EXPR2可以是上表中的任意⼀种测试条件,-a表示逻-
    [ EXPR1 -o EXPR2 ] :EXPR1和EXPR2可以是上表中的任意一种测试条件,-o表示-

if/then/elif/else/fi

#!/bin/bashif [ -d /bin ]; then        #开始    echo "/bin is a dir"fi      #结束
if :; then      #开始    echo "/ is always true"fi      #结束:是⼀个特殊的命令,称为空命令,该命令不做任何事,但Exit Status总是真

case/esac

#!/bin/bashread valcase $val in       #开始    a)    echo "enter val is a"    ;;    b)    echo "enter val is b"    ;;    *)    echo "enter val is *"    ;;esac        #结束

循环

for/do/done1. for i in {1..100}   do       echo "hello world\n"   done2. for(( i=0; i<100; i++ ))while/do/done1. while[$i -le 100]   do       echo "hello world\n"   done

函数(echo与return区别)

函数就像是迷你脚本,调用函数时可以传任意个参数,在函数内同样是用$0、$1、$2等变量来提取参数,函数中的位置参数相当于函数的局部变量,改变这些变量并不会影响函数外面的$0、$1、$2等变量。

  • 函数中可以用return命令返回,如果return后面跟一个数字则表示函数的Exit Status。
  • echo则可以返回任何类型,实际上都当作字符串输出,是一条输出语句

数组

#定义数组1. arr=""   arr[0]="123"   arr[1]="qwe"2. arr=("123" "qwe" "asd")#必须有空格隔开    arr1=("123"         "qwe"         "asd")#读取数组元素值的⼀一般格式是:1. ${array_name[index]}#使⽤用@ 或 * 可以获取数组中的所有元素:1. echo ${arr[*]}

运算符

  • 优先级 ! > && > ||
  • 逻辑运算符 < 关系运算符
  • 逻辑运算符 : ! && || -a -o
  • 关系运算符 : < > > \< == = != – eq –ne -gt -ge –lt -le

单引号和双引号

首先,单引号和双引号,都是为了解决中间有空格的问题。
因为空格在Linux中时作为一个很典型的分隔符,比如string1=this is astring,这样执行就会报错。为了避免这个问题,因此就产生了单引号和双引号。他们的区别在于,单引号将剥夺其中的所有字符的特殊含义,而双引号中的'$'(参数替换)和'`'(命令替换)是例外。所以,两者基本上没有什么区别,除非在内容中遇到了参数替换符$和命令替换符。
所以下面的结果:

num=3echo$num$numecho$num3

所以,如果需要在双引号””里面使用这两种符号,需要用反斜杠转义。

反引号"``"

这个东西的用法,我百度了一下,和$()是一样的。在执行一条命令时,会先将其中的 "``",或者是$()中的语句当作命令执行一遍,再将结果加入到原命令中重新执行,例如:

cho `ls`

会先执行 ls 得到xx.sh等,再替换原命令为:

echo xx.sh最后执行结果为xx.sh

那么,平时我们遇到的把一堆命令的执行结果输出到一个变量中,需要用这个命令替换符括起来,也就可以理解了。
这里又涉及到了一个问题,虽然不少系统工程师在使用替换功能时,喜欢使用反引号将命令括起来。但是根据POSIX规范,要求系统工程师采用的是$(命令)的形式。所以,我们最好还是遵循这个规范,少用“,多用$()

小括号,中括号,和大括号的区别

那么,下面又涉及到了一个问题,就是小括号,中括号,和大括号的区别。
先说说小括号和大括号的区别。这两者,实际上是“命令群组”的概念,也就是commandgroup。
( ) 把 command group 放在subshell去执行,也叫做 nested sub-shell。
{ } 则是在同一个 shell 內完成,也称为 non-namedcommand group。
所以说,如果在shell里面执行“函数”,需要用到{},实际上也就是一个命令群组么。
不过,根据实测,test=(lsa)test={ls–a}语法上面是有错误的。估计也和上面所说的原因有关。

另外,从网上摘录的区别如下:

  1. ()只是对一串命令重新开一个子shell进行执行
  2. {}对一串命令在当前shell执行
  3. ()和{}都是把一串的命令放在括号里面,并且命令之间用;号隔开
  4. ()最后一个命令可以不用分号
  5. {}最后一个命令要用分号
  6. {}的第一个命令和左括号之间必须要有一个空格
  7. ()里的各命令不必和括号有空格
  8. ()和{}中括号里面的某个命令的重定向只影响该命令,但括号外的重定向则影响到括号里的所有命令

两个括号(()),是代表算数扩展,就是对其包括的东西进行标准的算数计算——注意,不能算浮点数,如果需要算浮点数,需要用bc做。

至于中括号[],感觉作用就是用来比较的。比如放在if语句里面,while语句里面,等等。
这里引出来[..]和[[…]]的区别:(摘自网上,实测证实):使用[[… ]]条件判断结构, 而不是[ … ], 能够防止脚本中的许多逻辑错误.比如,&&, ||, <,和> 操作符能够正常存在于[[ ]]条件判断结构中, 但是如果出现在[ ]结构中的话,会报错。

[[ ]] 比[ ] 具备的优势

  1. [[是 bash 程序语言的关键字。并不是一个命令,[[ ]] 结构比[ ]结构更加通用。在[[和]]之间所有的字符都不会发生文件名扩展或者单词分割,但是会发生参数扩展和命令替换。

  2. 支持字符串的模式匹配,使用=~操作符时甚至支持shell的正则表达式。字符串比较时可以把右边的作为一个模式,而不仅仅是一个字符串,比如[[ hello == hell? ]],结果为真。[[ ]] 中匹配字符串或通配符,不需要引号。

  3. 使用[[ … ]]条件判断结构,而不是[… ],能够防止脚本中的许多逻辑错误。比如,&&、||、<和> 操作符能够正常存在于[[ ]]条件判断结构中,但是如果出现在[ ]结构中的话,会报错。

  4. bash把双中括号中的表达式看作一个单独的元素,并返回一个退出状态码。使用[[ … ]]条件判断结构, 而不是[ … ], 能够防止脚本中的许多逻辑错误. 比如,&&, ||, <, 和> 操作符能够正常存在于[[]]条件判断结构中, 但是如果出现在[ ]结构中的话, 会报错。

进度条编写

 i=1 str="" arr=("-" "/" "|" "\\") for i in {1..100} do     let j=i%4     printf "[%-100s][%d%%][%c]\r" "$str" "$i" "${arr[j]}"     sleep 0.1     str+="#" done echo ""

这里写图片描述