龙空技术网

Linux shell变量&运算符

星猿杂谈 198

前言:

此刻咱们对“linux shell 加减乘除”大约比较关注,各位老铁们都想要了解一些“linux shell 加减乘除”的相关资讯。那么小编在网上收集了一些有关“linux shell 加减乘除””的相关文章,希望各位老铁们能喜欢,同学们快快来了解一下吧!

注释

“# ”开头的就是注释,被编译器忽略

单行注释: #多行注释: :<Shell 变量

定义变量时,变量名不加美元符号($,PHP语言中变量需要),如:

your_name="runoob.com"

注意,变量名和等号之间不能有空格,这可能和你熟悉的所有编程语言都不一样。同时,变量名的命名须遵循如下规则:

命名只能使用英文字母,数字和下划线,首个字符不能以数字开头。中间不能有空格,可以使用下划线 _。不能使用标点符号。不能使用bash里的关键字(可用help命令查看保留关键字)。变量仅仅在声明时、赋值时、被删除时(unset)、被导出时(export),算术运算中使用双括号结构((...))时或在代表信号时才不需要有 $ 前缀。

除了显式地直接赋值,还可以用语句给变量赋值,如:

for file in `ls /etc`for file in $(ls /etc)

将 /etc 下目录的文件名循环出来。

变量类型

运行shell时,会同时存在三种变量:

局部变量:局部变量在脚本或命令中定义,仅在当前shell实例中有效,其他shell启动的程序不能访问局部变量。环境变量:所有的程序,包括shell启动的程序,都能访问环境变量,有些程序需要环境变量来保证其正常运行。必要的时候shell脚本也可以定义环境变量。shell变量:shell变量是由shell程序设置的特殊变量。shell变量中有一部分是环境变量,有一部分是局部变量,这些变量保证了shell的正常运行变量操作使用变量

使用一个定义过的变量,只要在变量名前面加美元符号即可,如:

your_name="qinjx"echo $your_nameecho ${your_name}

变量名外面的花括号是可选的,加不加都行,加花括号是为了帮助解释器识别变量的边界,比如下面这种情况:

for skill in Ada Coffe Action Java; do    echo "I am good at ${skill}Script"done

如果不给skill变量加花括号,写成echo "I am good at $skillScript",解释器就会把$skillScript当成一个变量(其值为空),代码执行结果就不是我们期望的样子了。

建议为所有变量加上花括号{}。

创建变量

local name="test" #(使用local修饰的变量在函数体外无法访问,并且local只能在函数体内使用) name="new_test" #(将原值覆盖)

只读变量

使用 readonly 命令可以将变量定义为只读变量,只读变量的值不能被改变。

 name="only_read"  或  readonly name #(使用readonly标识后的变量,不可被修改)
删除变量

使用 unset 命令可以删除变量。语法:

unset name

变量被删除后不能再次使用。unset 命令不能删除只读变量。

字符串变量单引号单引号变量var="my name is ${name}",只能原样输出,变量无效单引号中不能出现一个单独的单引号,转义也不可以双引号双引号变量var="my name is ${name}",变量有效可出现转义符拼接字符串中间无任何+,之类的字符name="this is"" my name"; name="this is my name"; name="this" is "my name" 等效name='this is'' my nam'; name='this is my name'; name='this' is 'my name' 等效获取字符串长度在${}中使用“#”获取长度

name="test";echo ${#name}; #输出为4
提取子字符串1:4 从第2个开始 往后截取4个字符::4 从第一个字符开始 往后截取4个字符
name="this is my name";echo ${name:1:4} #输出 is iecho ${name::4}  #输出 this
数组

bash只支持一维数组,不支持多维数组

定义数组:array_name=(li wang xiang zhang) (小括号做边界、使用空格分离)单独定义数组的元素: array_para[0]="w"; array_para[3]="s" (定义时下标不连续也可以)赋值数组元素:array_name[0]="zhao";获取数组元素:

array_name[0]="li"array_name[3]="zhang"echo ${array_name[0]} # 输出"li"echo ${array_name[1]} # 输出" "echo ${array_name[3]} # 输出"zhang"echo ${array_name[@]} # 输出"li zhang" 输出数组所有元素,没有元素的下标省略
取得元素个数:${#array_name[@]} 或者 ${#array_name}取得单个元素长度:${#array_name[1]}

特殊变量 参数传递

获取参数值:$0 : 固定,代表执行的文件名$1 : 代表传入的第1个参数$n : 代表传入的第n个参数$#:参数个数$*: 以一个单字符串显示所有向脚本传递的参数。如"$*"用「"」括起来的情况、以"$1 $2 … $n"的形式输出所有参数$@:与$*相同,但是使用时加引号,并在引号中返回每个参数。$$:脚本运行的当前进程号$!:后台运行的最后一个进程的ID$?: 显示最后命令的退出状态。0表示没有错误,其他任何值表明有错误。$* 与 $@ 区别相同点:都是引用所有参数。不同点:只有在双引号中体现出来。假设在脚本运行时写了三个参数 1、2、3,,则 " * " 等价于 "1 2 3"(传递了一个参数),而 "@" 等价于 "1" "2" "3"(传递了三个参数)。运算符算数运算+ 、-、*、\ : 乘号前必须加 \ 进行转义才可以进行乘法运算

运算操作符/运算命令

说明

(( ))

用于整数运算,效率很高,推荐使用

let

用于整数运算,和 (()) 类似。

$[]

用于整数运算,不如 (()) 灵活。

expr

可用于整数运算,也可以处理字符串。比较麻烦,需要注意各种细节,不推荐使用。

bc

Linux下的一个计算器程序,可以处理整数和小数。Shell 本身只支持整数运算,想计算小数就得使用 bc 这个外部的计算器。

declare -i

将变量定义为整数,然后再进行数学运算时就不会被当做字符串了。功能有限,仅支持最基本的数学运算(加减乘除和取余),不支持逻辑运算、自增自减等,所以在实际开发中很少使用。

(( ))的用法

运算操作符/运算命令

说明

((a=10+66)((b=a-15))((c=a+b))

这种写法可以在计算完成后给变量赋值。以 ((b=a-15)) 为例,即将 a-15 的运算结果赋值给变量 b。注意,使用变量时不用加$前缀,(( )) 会自动解析变量名。

a=$((10+66)b=$((a-15))c=$((a+b))

可以在 (( )) 前面加上$符号获取 (( )) 命令的执行结果,也即获取整个表达式的值。以 c=$((a+b)) 为例,即将 a+b 这个表达式的运算结果赋值给变量 c。注意,类似 c=((a+b)) 这样的写法是错误的,不加$就不能取得表达式的结果。

((a>7 && b==c))

(( )) 也可以进行逻辑运算,在 if 语句中常会使用逻辑运算。

echo $((a+10))

需要立即输出表达式的运算结果时,可以在 (( )) 前面加$符号。

((a=3+5, b=a+10))

对多个表达式同时进行计算。

数字关系运算符 注意空格

关系运算符只支持数字,不支持字符串,除非字符串的值是数字。

下面假定变量 a 为 10,变量 b 为 20

-eq :检测两个数是否相等,相等返回 true。 [ $a -eq $b ] 返回 false。-ne: 检测两个数是否不相等,不相等返回 true。 [ $a -ne $b ] 返回 true。-gt: 检测左边的数是否大于右边的,如果是,则返回 true。 [ $a -gt $b ] 返回 false。-lt : 检测左边的数是否小于右边的,如果是,则返回 true。 [ $a -lt $b ] 返回 true。-ge: 检测左边的数是否大于等于右边的,如果是,则返回 true。 [ $a -ge $b ] 返回 false。-le : 检测左边的数是否小于等于右边的,如果是,则返回 true。 [ $a -le $b ] 返回 true。字符串运算符

下表列出了常用的字符串运算符,假定变量 a 为 "abc",变量 b 为 "efg":

= :检测两个字符串是否相等,相等返回 true。 [ $a = $b ] 返回 false。!= :检测两个字符串是否相等,不相等返回 true。 [ $a != $b ] 返回 true。-z :检测字符串长度是否为0,为0返回 true。 [ -z $a ] 返回 false。-n :检测字符串长度是否为0,不为0返回 true。 [ -n "$a" ] 返回 true。$ :检测字符串是否为空,不为空返回 true。 [ $a ] 返回 true。布尔运算符

下表列出了常用的布尔运算符,假定变量 a 为 10,变量 b 为 20:

! :非运算,表达式为 true 则返回 false,否则返回 true。 [ ! false ] 返回 true。-o :或运算,有一个表达式为 true 则返回 true。 [ $a -lt 20 -o $b -gt 100 ] 返回 true。-a :与运算,两个表达式都为 true 才返回 true。 [ $a -lt 20 -a $b -gt 100 ] 返回 false。逻辑运算符

以下介绍 Shell 的逻辑运算符,假定变量 a 为 10,变量 b 为 20:

&& :逻辑的 AND [[ $a -lt 100 && $b -gt 100 ]] 返回 false|| :逻辑的 OR [[ $a -lt 100 || $b -gt 100 ]] 返回 true文件运算符-b file :检测文件是否是块设备文件,如果是,则返回 true。 [ -b $file ] 返回 false。-c file :检测文件是否是字符设备文件,如果是,则返回 true。 [ -c $file ] 返回 false。-d file :检测文件是否是目录,如果是,则返回 true。 [ -d $file ] 返回 false。-f file :检测文件是否是普通文件(既不是目录,也不是设备文件),如果是,则返回 true。 [ -f $file ] 返回 true。-g file :检测文件是否设置了 SGID 位,如果是,则返回 true。 [ -g $file ] 返回 false。-k file :检测文件是否设置了粘着位(Sticky Bit),如果是,则返回 true。 [ -k $file ] 返回 false。-p file :检测文件是否是有名管道,如果是,则返回 true。 [ -p $file ] 返回 false。-u file :检测文件是否设置了 SUID 位,如果是,则返回 true。 [ -u $file ] 返回 false。-r file :检测文件是否可读,如果是,则返回 true。 [ -r $file ] 返回 true。-w file :检测文件是否可写,如果是,则返回 true。 [ -w $file ] 返回 true。-x file :检测文件是否可执行,如果是,则返回 true。 [ -x $file ] 返回 true。-s file :检测文件是否为空(文件大小是否大于0),不为空返回 true。 [ -s $file ] 返回 true。-e file :检测文件(包括目录)是否存在,如果是,则返回 true。 [ -e $file ] 返回 true。逻辑判断符[ ]: 中括号旁边和运算符两边必须添加空格 (可以使用,不推荐)[[ ]]:中括号旁边和运算符两边必须添加空格 (字符串验证时,推荐使用)(()) : 中括号旁边和运算符两边必须添加空格 (数字验证时,推荐使用)[[]] 和 (()) 分别是[ ]的针对数学比较表达式和字符串表达式的加强版。使用[[ ... ]]条件判断结构,而不是[ ... ],能够防止脚本中的许多逻辑错误。比如,&&、||、<和> 操作符能够正常存在于[[ ]]条件判断结构中,但是如果出现在[ ]结构中的话,会报错。比如可以直接使用if [[ $a != 1 && $a != 2 ]], 如果不适用双括号, 则为if [ $a -ne 1] && [ $a != 2 ]或者if [ $a -ne 1 -a $a != 2 ]。

[[ ]] 中增加模式匹配特效;

(( ))不需要再将表达式里面的大小于符号转义,除了可以使用标准的数学运算符外,还增加了以下符号

命令替换符

Shell 命令替换是指将命令的输出结果赋值给某个变量。

命令替换与变量替换差不多,都是用来重组命令行的,先完成引号里的命令行,然后将其结果替换出来,再重组成新的命令行。

执行命令:

`ls /etc` : 反引号 (所有的unix系统都支持)$(ls /etc) : $() (部分unix系统不支持)

#!/bin/bashbegin_time=`date`    #开始时间,使用``替换sleep 20s            #休眠20秒finish_time=$(date)  #结束时间,使用$()替换echo "Begin time: $begin_time"echo "Finish time: $finish_time"#Begin time: 2019年 04月 19日 星期五 09:59:58 CST#Finish time: 2019年 04月 19日 星期五 10:00:18 CST

原则上讲,上面提到的两种变量替换的形式是等价的,可以随意使用;但是,反引号毕竟看起来像单引号,有时候会对查看代码造成困扰,而使用 $() 就相对清晰,能有效避免这种混乱。而且有些情况必须使用 $():$() 支持嵌套,反引号不行。

标签: #linux shell 加减乘除