Shell总结

变量

命名

由数字、字母、下划线组成
只能由字母、下划线开头

赋值

var="abc" 等号两边不能有空格

取值

$parameter

参数展开

${parameter}           如果参数后紧跟其他字符,大括号展开可以避免把参数当做其他参数
${parameter:-word}     如果变量存在且非null,则返回其值;否则返回word                     如果变量未定义,则返回默认值
${parameter:=word}     如果变量存在且非null,则返回其值;否则设置为word并返回 如果变量未定义,则设置变量为默认值
${parameter:?message}  如果变量存在且非null,则返回其值;否则显示parameter:message并退出 用来捕捉由于变量未定义而导致的错误
${parameter:+word}     如果变量存在且非null,则返回word;否则返回null                       测试变量是否存在
${parameter-word}      如果变量存在,则返回其值;否则返回word   如果变量未定义,则返回默认值
${parameter=word}      如果变量存在,则返回其值;否则设置为word并返回     如果变量未定义,则设置变量为默认值
${parameter?message}   如果变量存在,则返回其值;否则显示parameter:message并退出   用来捕捉由于变量未定义而导致的错误
${parameter+word}      如果变量存在,则返回word;否则返回null  测试变量是否存在。
${parameter#pattern}   如果模式匹配于开头处,则删除匹配的最短部分,并返回剩下的部分
${parameter##pattern}  如果模式匹配于开头处,则删除匹配的最长部分,并返回剩下的部分
${parameter%pattern}   如果模式匹配于结尾处,则删除匹配的最短部分,并返回剩下的部分
${parameter%%pattern}  如果模式匹配于结尾处,则删除匹配的最长部分,并返回剩下的部分
${#parameter}          返回变量值的字符长度

位置参数

$0     Shell程序的名称
$1-9	脚本参数,大于9时,用大括号括起来 ${10}
$#     脚本参数总个数
$*,$@  一次表示所有命令行参数
"$*"   将所有命令行参数视为单个字符
"$@"   将所有命令行参数视为单独的个体

特殊变量

-               在引用时给予Shell的选项
#               目前进程的参数个数
@               当前进程的命令行参数。置于双引号内,会把所有参数展开为一个个单独的字符串
*               当前进程的命令行参数。置于双引号内,会把所有参数展开为一个字符串
?               上一个命令的退出状态
$              Shell进程的进程ID
!               最近一个后台命令的进程ID。以此方式存储进程ID,可通过wait命令以供稍后使用
ENV             一旦引用,则仅用于交互式Shell中;$ENV的值是可展开的参数。结果应为要读取和在启动时要执行的一个文件的完整路径名称。这是一个XSI必需的变量
HOME            用户根目录
PATH            命令的查找目录
PWD             当前工作目录
IFS             内部的字段分隔器。例如,作为单词分隔器的字符列表。一般设为空格、制表符、以及换行
LANG            当前locale的默认名称;其他的LC_*变量会覆盖其值
LC_ALL          当前locale的名称;会覆盖LANG与其他LC_*变量
LC_COLLATE      用来排序字符的当前locale名称
LC_CTYPE        在模式匹配期间,用来确定字符类别的当前locale的名称
LC_MESSAGES     输出信息的当前语言的名称
LINENO          行号
NLSPATH         在$LC_MESSAGES(XSI)所给定的信息语言里,信息目录的位置
PPID            父进程的进程ID
PS1             主要的命令提示字符串。默认为"$"
PS2             行继续的提示字符串。默认为">"
PS4             以set -x设置的执行跟踪的提示字符串。默认为"+"

算数展开

$((expression))
括号内除了双引号,其他字符无需转义

退出状态

0       成功
1-125   由命令自己定义
126     命令找到了,但文件无法执行
127     命令找不到
>128    命令因收到信号而死亡
返回值为0-255,大于255的返回值都将被替换为该值除以256的余数

Shell命令

command

Shell命令的寻找顺序:
1. 特殊的内建命令
    . : break continue eval exec exit export readonly return set shift times trap unset
    1. 特殊内建命令语法上的错误,会导致Shell执行时退出;但一般内建命令语法的错误,不会导致Shell退出
        如果特殊内建命令遇到语法错误时不退出shell,则它的退出值应该非零???
    2. 以特殊内建命令所标明的变量指定,在命令完成后仍会有影响;一般内建命令或其他命令则不会
2. shell函数
3. 一般的内建命令
    alias bg cd command false fc fg getopts jobs kill newgrp pwd read true umask unalias wait
4. 外部命令

Pipeline

    [!] command1 [ | command2 ...]

List compound-list

    Asynchronous Lists
        command1 & [command2 & ... ]
        异步执行
    Sequential Lists
        command1 [; command2] ...
        顺序执行
    AND Lists
        command1 [ && command2] ...
        前面的命令执行成功才执行后面的命令
    OR Lists
        command1 [ || command2] ...
        前面的执行失败才执行后面的命令

AND-OR list

一个或多个pipelines,用"&&"和"||"分隔

list

一个或多个AND-OR lists,用";"和"&"分隔,以";"、"&"或"<newline>"结束

compound-list

一个或多个lists,前后可以跟多个<newline>
&&与||优先级相同,具有左结合性
false && echo foo || echo bar = ( false && echo foo ) || echo bar
true || echo foo && echo bar  = ( true || echo foo ) && echo bar

Compound command

Grouping Commands

subShell
    (compound-list)
    在子shell中执行,不改变主shell的环境。一般在新进程中执行,但也许不是
代码块
    { compound-list;}
    在当前进程中执行,会改变当前shell的环境
    }前必须有分号或换行符

for

for name [ in [word ... ]]
do
   compound-list
done
如果省略in word,则默认为in "$@"

case

case word in
    [(]pattern1) compound-list;;
    [[(]pattern[ | pattern] ... ) compound-list;;] ... 
    [[(]pattern[ | pattern] ... ) compound-list]
esac
最后一个compound-list,可以不加;;

if

if compound-list
then
    compound-list
[elif compound-list
then
    compound-list] ...
[else
    compound-list]
fi

while

while compound-list-1
do
            compound-list-2
done

until

until compound-list-1
do
            compound-list-2
done

函数

fname() compound-command[io-redirect ...]
$1,$2...$#,$*,$@都变成函数的位置参数,函数运行完毕后,原来的位置参数会被恢复
$0依旧是脚本名称

重定向

运算符
    set -C      打开noclobber选项,如果文件存在,则用>重定向输出时会失败,不会覆盖文件
    [n]<word    输入重定向
    [n]>word    输出重定向,如果文件存在,则覆盖文件
    [n]>|word   有移植性问题,避免使用。使noclobber选项失效
    [n]>>word   输出重定向,如果文件存在,则追加到文件末尾
    <<          here document
    <<-         here document,将所有开头的制表符删除(空格不删除)
    [n]<>word   有移植性问题,避免使用。打开一个文件作为输入输出
文件描述符处理
    [n]<&word   将输入重定向到文件描述符word
    [n]>&word   将输出重定向到文件描述符word
    shell脚本是否可以打开超过10个文件,由各shell自行决定,编程时需注意

波浪号展开与通配符

##波浪号展开##
    ~/xxx      将~展开为$HOME
    ~$user/xxx 	将~$user展开为用户XXX的根目录
##通配符展开##
    ?           任何单一字符
    *           任何字符串或字符
    [set]       任何在set里的字符
    [!set]      任何不在set里的字符
    通配符展开时,会忽略开头为.的文件,如果需要展开此类文件,需要在模式中明确提供.

命令替换

用命令的返回结果替换命令
$(command)
`command`

引用

\       字符的字面意思
''      将单引号之间的所有字符都当做字面意思
        不可以在单引号引用的字符串里在内嵌一个单引号
""      双引号内的转义、变量、算数、命令替换都会被处理
        单引号在双引号里没有特殊意义
        在双引号中,$、"、'、\这些符号,如果需要引用其字面意思,前面必须加上\

执行顺序

1. 将命令分割成tokens
2. 检查第一个token,开放的关键字/其他关键字/非关键字
3. 检查第一个token,别名/非别名
4. 波浪号展开
5. 变量展开
6. 命令替换
7. 算数展开
8. 对展开的文本进行单词分割
9. 通配符展开
10.命令查找:特殊内建命令->函数->一般内建命令->可执行文件
执行命令

内建命令

.

读取文件并于当前的Shell中执行文件中的内容
    . file
    如果file中不带/,则在$PATH中查找
    file不要求可执行,可读即可

:

不做任何事,只做参数的展开
    : [argument ...]

alias

隐藏或显示别名
alias [alias-name[=string] ...]
展开别名时不会递归展开

bg

break

break [n]       中断多少个被包含的循环

cd

改变工作目录
cd [−L | −P] [directory]
cd -            回到上一次的目录

command

在查找要执行的命令时,避开shell中的同名函数
command [−p] command_name [argument ...]
在函数中如果要执行同名的命令,可以用command xxx
-p 查找命令时,使用$PATH的默认值,而非当前的设置,确保能找到系统的工具

continue

continue [n]    继续多少个被包含的循环

eval

取出eval的参数,并再执行它一次
eval [argument ...]
var="ls | more"
$var ==> ls: more: No such file or directory   ls: |: No such file or directory
shell在执行时,把|和more当成了ls的参数。因为在步骤1时,shell解析管道字符|。而执行$var时,管道字符已经解析完毕,所以shell只把$var当做普通的变量展开
eval $var
将var的内容重新让shell解析并执行,执行正确

exec

重新执行一个程序,或改变I/O设置
exec [command [argument ...]]
exec 3< xxx     用文件描述符3读取xxx
exec 4> xxx     将文件描述符4输出至xxx
exec 5<&0       复制文件描述符0到文件描述符5
exec 3<&−       关闭文件描述符3
exec cat maggie 执行命令或程序时,exec为单项操作,控制权不可能再回到脚本,除非无法调用命令或程序

exit

使Shell返回一个退出值
exit [n]
如果没有参数,则以最后一个执行命令的退出状态作为默认的退出状态

export

输出或设置环境变量
export −p               输出环境变量(value有引号)
export name[=word]...   将name设为环境变量

false

什么都不做,返回一个false

fc

fg

getopts

getopts optstring name [arg...]
optstring       合法的选项字母字符串,如果字母后有:,则表示该选项需要一个参数
name            变量名称,每次调用getopts时,把当前处理的选项名称放到name中
OPTARG          如果选项有参数,放置到OPTARG中
OPTIND          下一个要处理的参数索引,一般调用完getopts后,通过shift $((OPTARG - 1))来删除所有处理过的参数

jobs

kill

newgrp

pwd

返回当前的目录
pwd[−L| −P]

read

从标准输入读取数据,并分配给变量
read [−r] var...
-r              读取原始数据,不做任何处理,不将结尾处的反斜杠解释为续行符
如果读取的信息多于变量,剩下所有的信息赋给最后一个变量
一旦遇到EOF,返回失败
IFS             决定read对输入的分隔符

readonly

输出或设置环境变量
    readonly −p                 输出环境变量(value有引号)
    readonly name[=word]...     将name设为环境变量

return

从函数中返回值
return [n]

set

显示所有Shell变量的名称与值;改变位置参数;打开或停用Shell选项
set                     显示所有Shell变量的名称与值
set c a c               Set $1, $2, and $3 and set "$#" to 3
set −−                  Unset all positional parameters
set −− "$x"				Set $1 to the value of x , even if it begins with ’−’ or ’+’
set −− $x              Set the positional parameters to the expansion of x , even if x expands with a leading ’−’ or ’+’
set -o                  显示当前设置
set +o                  显示当前设置,输出与-o有区别
set ±var                打开/停用shell选项
    -a  allexport       输出所有后续被定义的变量
    -b  notify          立即显示工作完成的信息,而不是等待下一个提示号。供交互使用
    -C  noclobber       不允许>重定向到以存在的文件。>|可以使此选项失效。攻交互使用
    -e  errexit         当命令以非0状态退出时,则退出Shell
    -f  noglob          停用通配符展开
    -h                  当函数被定义(而非函数被执行)时,寻找并记住从函数体中被调用的命令位置(XSI)
    -m  monitor         打开工作控制。供交互使用
    -n  noexec          读取命令且检查语法错误,但不要执行。交互式Shell被允许忽略此选项
    -u  nounset         视未定义的变量为错误,而非null
    -v  verbose         在执行命令前打印命令(逐字打印)
    -x  xtrace          在执行前先显示命令(展开后)
        ignoreeof       不允许以Ctrl-D退出Shell
        nolog           关闭函数定义的命令历史记录
        vi              使用vi风格的命令行编辑。供交互使用

shift

shift           一次将命令行参数向左移一位
shift digit     一次将命令行参数向左移digit位

times

打印运行时间
    %dm%fs %dm%fs   <shell user minutes>,    <shell user seconds>,    <shell system minutes>,    <shell system seconds>
    %dm%fs %dm%fs   <children user minutes>, <children user seconds>, <children system minutes>, <children system seconds>

trap

true

什么都不做,返回一个true

umask

unalias

删除别名的定义
unalias alias-name...   
unalias −a

unset

unset -v:       删除变量
unset -f:       删除函数

wait


其他命令

env

env:            输出环境变量(value没有引号)
-i:             初始化环境变量,启动命令
-u:             删除环境变量

test

test [expression]
[ [expression] ]
-e file     file存在
-s file     file不为空
-f file     file是一般文件
-d file     file是目录
-b file     file是块设备文件
-c file     file是字符设备文件
-p file     file是命名管道(FIFO)
-S file     file是socket
-h file     file是符号链接
-L file     file是符号链接,同-h
-r file     file是可读的
-w file     file是可写入的
-x file     file是可执行的,或file是可被查找的目录
-g file     file有设置setgid位
-u file     file有设置setuid位
string      string不是null
-n string   string非null
-z string   string是null
s1 = s2     字符串s1等于s2
s1 != s2    字符串s1不等于s2
n1 -eq n2   整数n1等于n2
n1 -ne n2   整数n1不等于n2
n1 -lt n2   整数n1小于n2
n1 -gt n2   整数n1大于于n2
n1 -le n2   整数n1小于等于n2
n1 -ge n2   整数n1大于等于n2
-t n        文件描述符n指向以终端

如果有多重条件,建议用shell级别的测试,而非-a -o
    if[ -f "abc" ] && [ -d "123" ]
所有的shell变量展开都应该用引号括起来
    if[ -f "$var" ]    正确
    if[ -f $var ]	错误,如果$var为空,则test接收的参数小于所需要的,后续行为无法预料
字符串比较时,在前面置一个其他字母
    if[ "X$var1" = "X$var2" ] 如果字符串为空,或者字符串开头带减号,则test命令容易混淆
只能进行整数测试

printf

printf format[argument...]
如果希望文字靠左显示,加-

basename

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值