严格来说,shell中没有表达式的概念。Shell本身事实上仅仅是一堆命令的集合。当然也不是胡乱的堆在一起。而是有一定的组织。仅仅是这个组织不那么严谨。所以本文不是要真的总结所谓的表达式,而是把shell中一些犄角旮旯的东西拼凑在一起。实在不知道它们属于那个分类。


  • 命令代换

    事实上就是这篇文章中的反引號所起的作用。可是命令代换还有还有一种形式,例如以下:
m@meng:~/scripts$ m=`date`
m@meng:~/scripts$ echo $m
2015年 06月 25日 星期四 10:40:24 CST
m@meng:~/scripts$ n=$(date)
m@meng:~/scripts$ echo $n
2015年 06月 25日 星期四 10:40:37 CST

也就是说,`command`和$(command)的效果是一样的。


  • 算术代换

    前面说过,将一个变量声明为整数类型时。它就能够做算术运算,或者说,赋值给这个变量的数字不再被当成字符串。而是真正的数字。假设没有这个整数声明。那么把一个数字或算术表达式赋值给一个变量时,它的值仍被视为普通字符串。

    可是如今,有还有一个方法能够达到这个效果,就是符号$((expr))。处于内括号里的变量将直接被视为整数。而不必事先声明其为整数类型。例如以下:

m@meng:~/scripts$ r=3+4
m@meng:~/scripts$ echo $r
3+4
m@meng:~/scripts$ echo $(($r))
7
m@meng:~/scripts$ echo $(($r+3))
10

只是,$(()) 中仅仅能用+-*/和()运算符,而且仅仅能做整数运算。


  • 引號

    Shell脚本中的单引號和双引號一样都是字符串的界定符,两者的差别在于,单引號中的全部字符都被视为普通字符。而舍弃其功能含义。比方’$’是变量值提取符,可是放在单引號中就是’\$’的字面值,例如以下:
m@meng:~/scripts$ q=5
m@meng:~/scripts$ echo "$q"
5
m@meng:~/scripts$ echo '$q'
$q

所以,在单引號中使用变量一定要小心。

所谓界定符。事实上就是将界定符内的字符串视为一个总体,而不会被空格等分隔符打断。

在双引號内,全部的特殊字符将保持其转义含义,如上面的’$’。假设想让双引號中的某个特殊字符恢复其本来面目。即取其字面值,能够在它前面加入转义字符’\’。例如以下:

m@meng:~/scripts$ echo "\$q"
$q

  • 退出状态

    在shell中,能够觉得一条命令就是一个表达式。

    表达式都是有值的。而一条命令的值是什么呢?是它的运行结果吗?比方ls列出来的文件?实际上。能够把命令的出口状态视为“命令表达式”的值:命令运行完毕后,会有一个出口状态来表示这条命令是否运行成功,普通情况下,shell中命令运行成功出口状态为0;失败为1或其它非0值。能够使用系统变量“#?”来查询上一条命令的出口状态。如:

m@meng:~/scripts$ grep m new
m@meng:~/scripts$ echo $?
1
m@meng:~/scripts$ cat new

m@meng:~/scripts$ echo $?
0
m@meng:~/scripts$ m=4
m@meng:~/scripts$ echo $? 0

上例,grep命令在new文件里没有找到字符”m”,所以其出口状态为1;其它都为0,包含赋值语句。

退出状态经经常使用做if语句的推断条件。


  • test表达式

    尽管能够直接使用命令的出口状态作为if、while等语句的推断条件,可是更常使用的却是test等专门的測试命令。

    test命令的语法为:

    test 表达式

    test主要用来运行三类測试:文件属性、数值比較、字符串比較。假设測试结果为真,则该命令的Exit Status为0,假设測试结果为假,则命令的Exit Status为1。

    • 文件測试

      格式为: test options file。基本的options包含:

      • -e 測试file的存在性,若存在则值为0;否则为1。这个结果跟运行普通命令得到的出口状态是一致的。

      • -d 測试file是否为文件夹,是为0。否为1。
      • -f 若file是普通文件,结果为真(即,值为0).
      • -s 測试文件是否为非空,若file存在且非空,为0;否则,即不存在或者是空文件,为1。
      • -r file存在且仅仅读,为真。
      • -w file存在且可写,为真。
      • -x file存在且可运行,为真。
    • 数字測试

      数字測试的比較运算符居然使用的是文字。对照方下(左側是C语言使用的传统的运算符。右側是shell使用的):

      == : -eq

      != : -ne

      > : -gt

      \< : -lt

      >= : -ge

      \<= : -le

    • 字符串測试

      -z str: 若str的长度是0。结果为真(谨记:真 <==> $? == 0)

      -n str: 若str的长度不是0,结果为真

      s1 = s2 : 两个字符串相等,结果为真

      s1 != s2 : 两个字符串不等。结果为真

      str : 不加不论什么选项来測试str。效果同-n


  • [ ] 表达式

    实际上。仅仅有 [ 是命令。而 ] 仅仅是界定符。[ 命令与test命令基本同样,唯一的差别就是格式不同,[ 命令须要将要測试的表达式置于括号里,###且表达式左右两边分别要和[ ]留一个空格###。如[ -z “empty” ]。

    据说,[ 命令的效率略微高一些,我没验证过。

    还有一点:###[ 命令不支持运算符“>”和“<”###。所以对于字符串比較运算的支持可能差一点,这是唯二的差别。。。。


  • [[ ]]表达式

    扩展了[ ]命令。首先就是支持了运算符“>”和“<”,另外还支持逻辑运算&&,||。!,例如以下:

m@meng:~/scripts$ [ er > et ]
m@meng:~/scripts$ echo $?
0
m@meng:~/scripts$ [[ er > et ]]
m@meng:~/scripts$ echo $? 1

显然,er > et结果应该为假,所以測试表达式的出口状态是1。

可是[]没有效果,而[[ ]]測试正确。

m@meng:~/scripts$ [ er > et || er < et ]
bash: [: 缺少 `]`
er:未找到命令
m@meng:~/scripts$ [[ er > et || er < et ]]
m@meng:~/scripts$ echo $?
0
m@meng:~/scripts$ [[ er > et && er < et ]]
m@meng:~/scripts$ echo $? 1

  • 算术表达式

    • (( ))表达式

      似乎有点凌乱了,(( ))与$(( ))的差别在于。后者能够把计算结果提取出来作为一个值使用,我个人感觉,’$’这个符号就是用来提取值的,比方引用变量的时候也用它。而符号(( ))仅仅是完毕计算本身,至于保存结果。尽管也能够,可是不是主业。还是直接看命令吧:
m@meng:~/scripts$ ((m=4-2))
m@meng:~/scripts$ echo $m
2
m@meng:~/scripts$ m=$((4-2))
m@meng:~/scripts$ echo $m
2

这意味着,((m=4-2))和m=$((4-2))效果是一样的。也就是说在(())内部能够直接完毕赋值。

~~~~

m@meng:~/scripts$ echo $((4-2))
2
m@meng:~/scripts$ echo ((4-2))
bash: 未预期的符号 '(' 附近有语法错误

这说明。(())不负责保存结果,想要结果的话,用’$’来提取。

~~~~

m@meng:~/scripts$ m=3;n=2
m@meng:~/scripts$ echo $((m-n))
1

这说明,在(())内部使用变量时,不须要加入’$’符号。

~~~~

m@meng:~/scripts$ m=3;n=2
m@meng:~/scripts$ echo $((m<n))
0
m@meng:~/scripts$ echo $((m>n))
1

显然,(())还支持比較运算,唯一的问题是。它的出口状态与test等其它命令恰好相反!

~~~~

总结一下这个表达式:

1、仅仅支持整数运算。

2、支持的运算包含:=(赋值)、==(相等)、>= <= < > % + - * / -= += /= *= %=。非常丰富了。

  • let表达式

    与上面那个基本一样。仅仅是格式不同罢了。let中表达式写在let后面。而不是括号里。另外,因为不像(())有天然的界定符。所以算式中有空格时,须要用引號括起来。

  • expr表达式

    以后再写吧。好累。。。上面的已经够用了。


逻辑运算

主要有&&、||、-a、-o、!和(),用来计算表达式之间的逻辑运算。支持用括号()来进行组合,逻辑运算符和表达式之间要有空格

[[]]命令仅仅支持符号,不支持-a和-o选项。

m@meng:~/scripts$ [[ er > et -o er < et ]]
bash: 条件表达式中有语法错误
bash: '-o' 附近有语法错误

完。

Linux Shell之表达式的更多相关文章

  1. linux shell 常用表达式汇总

    1. linux shell 逻辑运算符.逻辑表达式详解: http://www.cnblogs.com/chengmo/archive/2010/10/01/1839942.html

  2. Linux - Shell - 算术表达式 - 算数运算

    概述 shell 中基于 $(()) 的 算数运算 背景 复习 shell 脚本 凑数吧 准备 环境 os centos7 1. 算数运算 代码 #!/bin/bash # $(()) 的数学运算, ...

  3. Linux - Shell - 算数表达式 - 关系运算

    概述 shell 中基于 $(()) 的 关系运算 背景 复习 shell 脚本 凑数吧 准备 环境 os centos7 1. 位运算 代码 #!/bin/bash # 关系运算符 # 结果是 真/ ...

  4. Linux - Shell - 算数表达式 - 位运算

    概述 shell 中基于 $(()) 的 位运算 背景 复习 shell 脚本 凑数吧 准备 环境 os centos7 1. 位运算 代码 #!/bin/bash # 位运算 arg1=2 arg2 ...

  5. Linux shell中的一个问题 ${}带正则匹配的表达式

    目前在准备龙芯项目的PMON,在研究其编译过程的时候,看到一些make 语句,百思不得其解.后来在shell编程中看到一点资料,牵扯到Shell中的正则表达式.故记录下来,以备后来查阅. 问题: 在某 ...

  6. Linux shell脚本编程(三)

    Linux shell脚本编程 流程控制: 循环语句:for,while,until while循环: while CONDITION; do 循环体 done 进入条件:当CONDITION为“真” ...

  7. Linux shell脚本编程(二)

    Linux shell脚本编程(二) 练习:求100以内所有偶数之和; 使用至少三种方法实现; 示例1: #!/bin/bash # declare -i sum=0 #声明一个变量求和,初始值为0 ...

  8. Linux shell脚本编程(一)

    Linux shell脚本编程: 守护进程,服务进程:启动?开机时自动启动: 交互式进程:shell应用程序 广义:GUI,CLI GUI: CLI: 词法分析:命令,选项,参数 内建命令: 外部命令 ...

  9. 【shell 大系】Linux Shell常用技巧

    在最近的日常工作中由于经常会和Linux服务器打交道,如Oracle性能优化.我们数据采集服务器的资源利用率监控,以及Debug服务器代码并解决其效率和稳定性等问题.因此这段时间总结的有关Linux ...

随机推荐

  1. android中一些特殊字符(如:←↑→↓等箭头符号)的Unicode码值

    在项目中,有时候在一些控件(如Button.TextView)中要添加一些符号,如下图所示:                          这个时候可以使用图片的方式来显示,不过这些可以直接使用U ...

  2. 手写一个自己的LocalCache - 基于LinkedHashMap实现LRU

    功能目标      实现一个全局范围的LocalCache,各个业务点使用自己的Namespace对LocalCache进行逻辑分区.所以在LocalCache中进行读写採用的key为(namespa ...

  3. 默认网关和默认路由 —— Cisco CCNA – Default Gateway & Default Routes

    原文:https://www.certificationkits.com/cisco-certification/ccna-articles/cisco-ccna-intro-to-routing-b ...

  4. VS2008+Windows DDK 7的环境配置(二)

    在第一篇的基础上,进行如下的步骤,就可以编译出X64的驱动程序. (建议再另外建一个项目,这样避免混淆,因为x86和x64编译的有些编译选项是不同的.) 1. 安装VS2008 x64 build 组 ...

  5. Discuz上传错误

    换了服务器后,上传图片的时候,显示上传100%,然后报错:upload error: 500.怎么回事那? [解决方法] 原来是php上传文件的时候,会首先上传到一个临时目录.如果临时目录没有权限,就 ...

  6. SqlServer 之 系统视图

    一.了解系统视图 1. 系统视图:从名字上看就知道,就是存放一些sqlserver系统的一些信息. 2. 存在位置: 下面截图看看,从截图中你可以看到,不管是“系统数据库”还是“用户数据库”都是有这些 ...

  7. Java从零开始学二十(集合简介)

    一.为什么需要集合框架 数组的长度是固定的,但是如果写程序时并不知道程序运行时会需要多少对象.或者需要更复杂的方式存储对象,---那么,可以使用JAVA集合框架,来解决这类问题 二.集合框架主要接口 ...

  8. Swift学习笔记(十五)——程序猿浪漫之用Swift+Unicode说我爱你

    程序猿经常被觉得是呆板.宅,不解风情的一帮人.可是有时候.我们也能够使用自己的拿手本领来表现我们的浪漫. 因为Swift语言是支持Unicode编码的,而Unicode最新已经支持emoji(绘文字) ...

  9. 1z0-052 q209_3

    3: Identify two situations in which you can use Data Recovery Advisor for recovery. (Choose two.) —° ...

  10. ZOJ2750_Idiomatic Phrases Game(最短路)

    Idiomatic Phrases Game Time Limit: 2 Seconds      Memory Limit: 65536 KB Tom is playing a game calle ...