第二章 shell的语法
变量:字符串、数字、环境和参数
获取变量内容可以在变量前使用$字符,使用echo指令可以将变量内容输出到终端。
wuchao@wuchao-Lenovo:~$ var=hello
wuchao@wuchao-Lenovo:~$ echo $var
hello
wuchao@wuchao-Lenovo:~$ var=+
wuchao@wuchao-Lenovo:~$ echo $var
+
注意:如果字符串中间有空格,则必须使用引号。此外等式两边不能有空格。
使用read命令可以将用户输入的值赋给变量
wuchao@wuchao-Lenovo:~$ read var
hello world
wuchao@wuchao-Lenovo:~$ echo $var
hello world
引号的使用
双引号中使用$var时,程序自动替换成变量的值。单引号中使用$var时,不会发生替换。如果想把$当作普通字符,则在$使用\取消它的特殊含义。
wuchao@wuchao-Lenovo:~$ var="hello world"
wuchao@wuchao-Lenovo:~$ echo $var
hello world
wuchao@wuchao-Lenovo:~$ echo "$var"
hello world
wuchao@wuchao-Lenovo:~$ echo '$var'
$var
wuchao@wuchao-Lenovo:~$ echo \$var
$var
环境变量
$HOME :当前home目录
$PATH :搜索命令的目录
$0 :shell脚本的名字
$# :传递给脚本的参数的个数
$$ :shell脚本的进程号
参数变量
$1 , $2,…… :脚本程序的参数
$* :在一个变量中列出所有参数,使用IFS环境变量作为分隔符
$@ :$*的变体。但不使用IFS环境变量
wuchao@wuchao-Lenovo:~/linux_program$ cat test02
#!/bin/sh
var=hello
echo "value of var is: $var"
echo "runing"
echo "this shell name is $0"
echo "the first param is $1"
echo "the second param is $2" wuchao@wuchao-Lenovo:~/linux_program$ ./test02 Hell World
value of var is: hello
runing
this shell name is ./test02
the first param is Hell
the second param is World
wuchao@wuchao-Lenovo:~/linux_program$
条件:shell中的boolean值
shell的boolean判断常常使用test或[命令。其中[命令可以使用]结尾。
比如测试hello.h文件是否存在:
if test -f hello.h
then
...
fi
或者
if [ -f hello.h ]
then
...
fi
注意:[后面必须有空格
test命令归为一下三类:
字符串比较
string1 = string2 相同为真
string1 != string2 不同为真
-n string1 判断字符串是否为非0,字符为空时为false
-z string1 判断字符串是否为0,字符串为null时为true
算术比较
expression1 -eq expression2 表达式结果相等
expression1 -ne expression2 表达式结果不相等
expression1 -gt expression2 前者大于后者
expression1 -ge expression2 前者大于等于后者
expression1 -lt expression2 前者小于后者
expression1 -le expression2 前者小于等于后者
文件条件测试
-d file 测试文件是否是一个目录
-e file 测试文件是否存在
-f file 测试文件是否是一个普通文件
-g file 如果文件的set-group-id位被设置则为真
-r file 测试文件是否可读
-s file 测试文件大小是否不为0
-u file 如果文件的set-user-id位被设置则为真
-w file 测试文件是否可写
-x file 测试文件是否可执行
程序控制:if、elif、for、while、until、case
if语句
if condition
then
statements
else
statements
fi
elif语句
if condition
then
statements
elif
then
statements
else
statements
fi
for循环
for variable in values
do
statements
done
举例:
wuchao@wuchao-Lenovo:~/linux_program$ cat test02
#!/bin/sh for var in hello world cc
do
echo $var
done exit wuchao@wuchao-Lenovo:~/linux_program$ ./test02
hello
world
cc
使用通配符的for循环
打印所有以foo开头并以.sh结尾的文件
wuchao@wuchao-Lenovo:~/linux_program$ ls foo*.sh
foo01.sh foo02.sh foo03.sh
wuchao@wuchao-Lenovo:~/linux_program$ cat test02
#!/bin/sh for var in $(ls foo*.sh)
do
echo $var
done exit wuchao@wuchao-Lenovo:~/linux_program$ ./test02
foo01.sh
foo02.sh
foo03.sh
while语句
while condition
do
statements
done
until语句
until condition
do
statements
done
case语句
case variable in
pattern [ | pattern ] ...) statements;;
pattern [ | pattern ] ...) statements;;
...
esac
注:每个模式下都可以放置多条语句,因此使用;;表示模式的结束。
case示例一:
wuchao@wuchao-Lenovo:~/linux_program$ cat test02
#!/bin/sh
echo "please input you choice (y,yes,n,no)"
read choice;
case "$choice" in
y ) echo "your choice is yes";;
yes ) echo "your choice is yes";;
n ) echo "your choice is no";;
no ) echo "your choice is no";;
* ) echo "wrong input";;
esac
exit wuchao@wuchao-Lenovo:~/linux_program$ ./test02
please input you choice (y,yes,n,no)
yes
your choice is yes
wuchao@wuchao-Lenovo:~/linux_program$ ./test02
please input you choice (y,yes,n,no)
d
wrong input
case语句当匹配到以后,不会再继续匹配后面的模式。使用通配符*可以匹配所有情况。
case示例二:合并匹配模式
wuchao@wuchao-Lenovo:~/linux_program$ cat test02
#!/bin/sh
echo "please input you choice (y,yes,n,no)"
read choice;
case "$choice" in
y|yes ) echo "your choice is yes";;
n|no ) echo "your choice is no";;
* ) echo "wrong input";;
esac
exit wuchao@wuchao-Lenovo:~/linux_program$ ./test02
please input you choice (y,yes,n,no)
y
your choice is yes
case示例三:执行多条语句
wuchao@wuchao-Lenovo:~/linux_program$ cat test02
#!/bin/sh
echo "please input you choice a num (0-2)"
read choice;
case "$choice" in
) echo "num is 0";
echo "num is 0";;
) echo "num is 1";
echo "num is 1";;
) echo "num is 2";
echo "num is 2";;
* ) echo "bad input";
echo "bad input";;
esac
exit wuchao@wuchao-Lenovo:~/linux_program$ ./test02
please input you choice a num (-) num is
num is
wuchao@wuchao-Lenovo:~/linux_program$ ./test02
please input you choice a num (-) bad input
bad input
命令列表
AND列表
statement1 && statement2 && statement3 ……
只有前面的命令执行成功后才执行后一条。&&用于测试前一条语句是否成功执行,成功的话执行后一句。
OR列表
statement1 || statement2 || statement3 ……
直到某一个命令执行成功才结束,即当前面的命令返回false时才执行下一条。||用于测试前一条语句是否成功执行,失败的话执行后一句。
函数
函数必须在调用前定义。
函数被调用时,脚本程序的位置参数($*,$@,$#,S1,$2等)会被替换成函数的参数。执行完毕后在恢复原来的值。
举例:
#!/bin/sh #以下为函数
yes_or_no(){
echo "Is your name $* ?"
while true
do
echo -n "Enter yes or no:"
read x
case "$x" in
y | yes ) return ;;
n | no ) return ;;
* ) echo "Anser yes or no"
esac
done
} #以下为主程序
echo "Original params are $*"
if yes_or_no "$1"
then
echo "Hi $*,nice name"
else
echo "Never mind"
fi exit
yes_or_no "$1"表示执行yes_or_no函数,并传递变量$1给函数 执行结果
wuchao@wuchao-Lenovo:~/linux_program$ ./test02 wu chao
Original params are wu chao
Is your name wu ?
Enter yes or no:y
Hi wu chao,nice name
注意:shell中命令执行成功时返回状态码0,失败返回非0,故if遇到0时,为真。比如上面的例子。函数yes_or_no返回0时,主程序的if语句才执行then后面的语句。
shell内置命令
break 命令
跳出一层循环
: 命令
空命令,相当于true的别名。
continue 命令
跳到下一次循环,继续执行。
. 命令
一般情况下,当脚本执行一条外部命令或脚本程序时会创建一个新的环境,命令将在新的环境下执行,结束后退回父shell。但外部的source命令和.命令(两个命令一致)在执行脚本程序中列出的命令时,使用的是调用该脚本程序的同一个shell。因此使用.命令执行程序,可以改变当前shell的环境变量,程序结束后,环境变量仍然有效。
比如以下脚本:
# test.sh
echo “shell is runing”
exit
当执行./test.sh时,终端显式“shell is runing”,当执行. ./test.sh时,由于脚本最后一行exit 是退出shell,结果当前shell被关闭。
echo 命令
echo默认输出带换行符的字符串。可以使用echo -n “string”来输出不换行的字符串。
eval 命令
对参数进行求值。(个人理解为将字符串解析成命令)
举例:
wuchao@wuchao-Lenovo:~/linux_program$ foo=
wuchao@wuchao-Lenovo:~/linux_program$ x=foo
wuchao@wuchao-Lenovo:~/linux_program$ y='$'$x
wuchao@wuchao-Lenovo:~/linux_program$ echo $y
$foo
wuchao@wuchao-Lenovo:~/linux_program$ eval y='$'$x
wuchao@wuchao-Lenovo:~/linux_program$ echo $y
exec命令
将当前shell替换为一个不同的程序。
exit n 命令
交互式shell使用该命令时会使你退出系统。
export 命令
将作为它参数的变量导出到子shell中,并使之生效。默认下,一个shell中被创建的变量在这个shell调用的子shell中是不可用的。export将自己的参数创建为一个环境变量,而这个环境变量是可以被当前程序调用的其他脚本和程序读取的。
(个人理解:父进程的一般变量,子进程不能访问,而环境变量可以)
外部命令和shell脚本执行时,会创建新的shell,内置命令好像不创建新的shell。
expr 命令
将它的参数当作表达式求值。
比如:x=`expr $x + 1` 或 x=$(expr $x + 1) (注意+左右的空格)
反引号(``)使x的取值为expr $x + 1的执行结果。也可以用$()替换反引号。
expr现在被$((...))替代了。
如:x=$(($x + 1))
printf 命令
类似于c++的printf
格式化字符串然后被用来解释后续参数的含义并输出结果。
wuchao@:~$ printf "%s %d\t%s" "Hi There" 15 people
Hi There 15 people
return 命令
函数返回值
set 命令
为shell设置参数变量
shift 命令
把所有参数变量左移一个位置,使$2变成$1,$3变成$2……,$0保持不变。
wuchao@:~/linux_program$ cat test02
#!/bin/sh
while [ "$1" != "" ];
do
echo "$1"
shift
done
exit wuchao@:~/linux_program$ ./test02 aa bb cc
aa
bb
cc
trap 命令
指定在接收到信号时将要采取的行动。
trap command signal
信号 | 说明 |
HUP(1) | 挂起,通常因终端掉线或用户退出而引发 |
INT(2) | 中断,通常因Ctrl+C组合键而引发 |
QUIT(3) | 退出,通常因Ctrl+\组合键而引发 |
ABRT(6) | 中止,通常因严重的执行错误而引发 |
ALRM(14) | 报警,通常用来处理超时 |
TERM(15) | 终止,通常在系统关机时发送 |
unset 命令
从环境中删除变量或函数。
find 命令
格式:
find [path] [options] [tests] [actions]
选项 | 含义 |
-depth | 在查看目录本身之前先搜索目录的内容 |
-follow | 跟随符号链接 |
-maxdepths N | 最多搜索N层目录 |
-mount(或-xdev) | 不搜索其他文件系统的目录 |
下面是测试部分,每种测试返回的结果有两种可能:true和false。find命令开始工作时,按照顺序将每种测试应用到它搜索到的每个文件,如果返回false,find停止处理当前找到的文件,并继续搜索。如果返回true,find将继续下一个测试或对当前文件采取行动(actions)。
测试 | 含义 |
-atime N | 文件在N天前被访问过 |
-mtime N | 文件在N天前被修改过 |
-name pattern | 文件名匹配提供的模式pattern,为了确保pattern被传递给find而不是由shell处理,pattern必须被引号括起。 |
-newer otherfile | 文件比otherfile新 |
-type c | 文件的类型是c(常见的是d和f) |
-user username | 文件的拥有者 |
还可以使用操作符来组合测试
操作符,短格式 | 操作符,长格式 | 含义 |
! | -not | 测试取反 |
-a | -and | 两个测试必须为真 |
-o | -or | 两个测试必须有一个为真 |
可以使用圆括号来强制优先级。括号需要使用反斜杆。如果文件名处使用的是匹配模式,则此处必须用引号。
如:\(-newer X -o -name "_*" \)
动作 | 含义 |
-exec command | 执行一条命令,后面跟一个{}用于表示当前的完整路径,然后以 \;结束。 |
-ok command | 同上,只不过每次询问用户。 |
打印文件名 | |
-ls | 对当前文件使用ls -dils |
举例:
在当前目录查找比bill.c文件更新的文件,并且使用ls -l命令处理这些找到的文件。
wuchao@:~/linux_program$ find . -newer bill.c -type f -exec ls -l {} \;
-rw-rw-r-- wuchao wuchao 10月 : ./test01.sh
-rw-rw-r-- wuchao wuchao 10月 : ./fred.o
-rw-rw-r-- wuchao wuchao 10月 : ./program.o
-rw-rw-r-- wuchao wuchao 10月 : ./bill.o
-rwxrwxr-x wuchao wuchao 10月 : ./a.out
-rwxrwxr-x wuchao wuchao 10月 : ./program
-rw-rw-r-- wuchao wuchao 10月 : ./program.c
-rw-rw-r-- wuchao wuchao 10月 : ./foo01.sh
-rw-rw-r-- wuchao wuchao 10月 : ./foo02.sh
-rw-rw-r-- wuchao wuchao 10月 : ./libfoo.a
-rwxrw-r-- wuchao wuchao 10月 : ./test02
-rw-rw-r-- wuchao wuchao 10月 : ./lib.h
-rw-rw-r-- wuchao wuchao 10月 : ./foo03.sh
grep 命令
参数:
grep [options] pattern [files]
选项 | 含义 |
-c | 输出匹配行的数目,而不是匹配行 |
-E | 启用扩展表达式 |
-h | 取消每个输出行的普通前缀,即匹配查询模式的文件名 |
-i | 忽略大小写 |
-l | 只列出包含匹配行的文件名,而不是匹配行 |
-v | 对匹配模式取反 |
正则表达式
常用的特殊字符
字符 | 含义 |
^ | 指向一行的开头 |
$ | 指向一行的结尾 |
. | 任意单个字符 |
[] | 方括号内的一个字符访问,其中任何一个字符都可以被匹配,例如字符范围a~e,或在字符范围前面加上^符号表示取反向字符范围。 |
特殊匹配模式
匹配模式 | 含义 |
[:alnum:] | 大小写字符及数字,0-9,A-Z,a-z |
[:alpha:] | 英文大小写字符 |
[:blank:] | 空格键与tab键 |
[:cntrl:] | 控制按键,CR,LF,TAB,DEL等 |
[:digit:] | 代表数字 |
[:graph:] | 除空格符(空格和Tab)外其他按键 |
[:lower:] | 小写字符 |
[:print:] | 可以被打印出来的字符 |
[:punct:] | 标点字符," ' ? ; : # $ |
[:upper:] | 大写字符 |
[:space:] | 任何会产生空白的字符 |
[:xdigit:] | 十六进制数字 |
基础正则表达式字符
选项 | 意义 | |
^word | 带查找的字符串在行首 | |
word$ | 待查找的字符串在行尾 | |
. | 代表一定有一个任意字符的字符 | |
\ | 转义字符 | |
* | 重复零到无穷多个前一个字符 | |
[list] | 从字符集合的RE字符里找到想要选取的字符 | |
[n1-n2] | 从字符集合的RE字符里找到想要选取的字符范围 | |
[^list] |
|
|
\{n,m\} | 前一个字符重复n到m次 |
命令的执行
捕获命令的执行结果: $(command)
算术扩展
$((...))
wuchao@:~/linux_program$ cat test02
#!/bin/sh
x=
while [ "$x" -ne ];do
echo $x
x=$(($x+))
done
exit wuchao@:~/linux_program$ ./test02 wuchao@:~/linux_program$
参数扩展
参数扩展 | 说明 |
${param:-default} | 若 param 未定义或为空,则返回 default,否则返回 param 的值 |
${param-string} | 若 param 未定义,则返回 string,否则返回 param 的值 |
${param:+string} | 若 param 为非空,则返回 string,否则返回 param 的值 |
${#param} | 给出param的长度 |
${param%word} | 从param的尾部开始删除与word匹配的最小部分,返回剩余部分 |
${param%%word} | 从param的尾部开始删除与word匹配的最长部分,返回剩余部分 |
${param#word} | 从param的头部开始删除与word匹配的最小部分,返回剩余部分 |
${param##word} | 从param的头部开始删除与word匹配的最长部分,返回剩余部分 |
here文档
本章节应用程序设计
查看程序请点击这里。
第二章 shell的语法的更多相关文章
- java面向对象编程——第二章 java基础语法
第二章 java基础语法 1. java关键字 abstract boolean break byte case catch char class const continue default do ...
- 第二章 JavaScript核心语法
第二章 avaScript核心语法 一.变量的声明和赋值 JavaScript是一种弱类型语言,没有明确的数据类型,也就是在声明变量时不需要指定数据类型,变量的类型由赋给变量的值决定. 在Java ...
- 第二章 Java 基本语法1
2.1关键字 1.定义:被Java语言赋予了特殊含义,用做专门用途的字符串(单词). 2.特点:关键字中所有字母都是小写字母. 3.分类: 用于定义数据类型的关键字:byte.short.int.lo ...
- PHP-----PHP程序设计基础教程----第二章PHP基本语法
博文结构: 2.1 PHP语法风格 2.1.1 PHP标记 PHP有四种风格的标记,具体如表2-1所示: 表2-1 PHP开始和结束标记 标记类型 开始标记 结束标记 示例 说明 标准标记 <? ...
- 新手小白入门C语言第二章:基本语法
1. 语句 C 语言的代码由一行行语句(statement)组成.语句就是程序执行的一个操作命令.C 语言规定,语句必须使用分号结尾,除非有明确规定可以不写分号. 如: int x = 1; 这就是一 ...
- 第二章 Python基础语法
2.1 环境的安装 解释器:py2 / py3 (环境变量) 开发工具:pycharm 2.2 编码 编码基础 ascii ,英文.符号,8位为一个东西,2**8 unicode ,万国码,可以表示所 ...
- 第二章 python基本语法元素
python有两种编程方式,交互式和文件式. 交互式:对每个输入语句即时运行结果------适合语法练习 文件式:批量执行一组语句并运行结果------编程的主要方式 实例1:圆面积的计算(根据半径r ...
- 第二章 初始MySQL 语法
1.使用MySQL的优势 运行速度快.MySQL体积小,命令执行的速度快: 使用成本低.MySQL是开源的. 容易使用. 可移植性强.MySQL能够运行于多种系统平台之上,windows,linux, ...
- [转]Windows Shell 编程 第二章 【来源:http://blog.csdn.net/wangqiulin123456/article/details/7987893】
第二章Shell的结构 “Shell 编程”的大伞之下有大量的API函数和COM接口.这个种类繁多的‘命令’集允许你用不同的方法对Windows Shell进行编程.函数和接口并不是两种提供相同功能 ...
随机推荐
- FileBeats安装
FileBeats安装 FileBeats官方下载链接: https://www.elastic.co/downloads/beats/filebeat 也可以直接使用以下命令下载(文章下载目录一概为 ...
- laravel 闪存
https://blog.csdn.net/ckdecsdn/article/details/52083093
- 第一篇:百问网ubuntu安装注意事项和部分配置
目录 一.开启虚拟化技术 二.ubuntu部分设置 一.开启虚拟化技术 64位机,需要使用cpu-z.SecurAble软件来检查:CPU是否支持VT虚拟化技术 cpu-z使用(软件) 第一步:以 ...
- mvc:interceptor拦截器使用
在spring-mvc.xml里面配置标签 <mvc:interceptors> <mvc:interceptor> <mvc:mapping path="/* ...
- 第三节 循环链表的Go语言实现
一.什么是循环链表 循环链表的节点形成一个圈.把单链表的尾巴指向开头形成单循环链表.把双向链表的尾巴与开头链接起来就形成双向循环链表.使用循环链表可以不断的绕圈寻找所需要的数据,而不需要像单链表那样每 ...
- Java中的IO
引言: 对程序语言的设计者来说,创建一个好的输入/输出(I/O)系统是一项艰难的任务 < Thinking in Java > 本文的目录视图如下: Java IO概要 a ...
- 洛谷九月月赛T1 思考
很迷的一道题目,刚开始直接枚举n个1,然后去mod m ,爆0,后来发现一个神奇性质:找到递推公式An=An-1*10+1,枚举n,不断mod m,每递推一次就1的个数加一.居然可行! 听说余数具有可 ...
- Java设计模式(5)——创建型模式之建造者模式(Builder)
一.概述 概念 将一个复杂的构建与其表示相分离,使得同样的构建过程可以创建不同的表示.(与工厂类不同的是它用于创建复合对象) UML图 主要角色 抽象建造者(Builder)——规范建造方法与结果 ...
- 厦门Uber优步司机奖励政策(1月11日~1月17日)
滴快车单单2.5倍,注册地址:http://www.udache.com/ 如何注册Uber司机(全国版最新最详细注册流程)/月入2万/不用抢单:http://www.cnblogs.com/mfry ...
- spring源码-BeanFactoryPostProcessor-3.2
一.BeanFactoryPostProcessor这个是spring容器的拓展之一,其目的是在容器初始化完成之前,通过beanFactory对上下文进行进行操作. 二.常用场景,需要对beanDef ...