第一章:shell 基础
● umask
eg:
[test@szbirdora 1]$umask
0002
[test@szbirdora 1]$ls -lh
-rw-rw-r--
drwxrwxr-x
上面的例子中我们看到由test 默认创建的文件myfile 和文件夹1 的权限分别为664 ,775.而通过umask查到的默认权限为002.所以可以推断出umask的计算算法为:
umask
0
1
2
3
4
5 1
6 0
7 0
●连接ln
硬连接 ln sourcefile targetfile
软连接 ln -s sourcefile targetfile
●shellscript基本结构
# !/bin/bash
# description
variable name=value
control segment
eg.
helloworld.sh
#! /bin/bash
# This is a helloworld shell script
printchar = "hello world"
echo $printchar
[test@szbirdora 1]$shhelloworld.sh
hello world
●shell特性
① 别名
② 管道
③ 命令替换
④ 后台运行
⑤ 重定向
⑥ 变量
⑦ 特殊字符
第二章:变量和运算符
●本地变量:在用户现在的shell 生命期的脚本中使用。设置变量:various_name=value.可用set 来查看。用readonly 可以使变量只读。
● 环境变量:用于当前用户下所有用户进程(不限于现在的shell )。
● 变量替换
echo ${variable name}
echo ${variablename:+value}
echo ${variablename:?value}
echo ${variable name:-value}
echo ${variable name:=value}
● 清除变量
● 位置变量
位置变量表示$0,$1,$2...$9
$0 ---- 脚本名字
$1 ----根据参数位置表示参数1
eg.
#! /bin/bash
#parm.sh
echo "This is script name : $0"
echo "This is parameter 1: $1"
echo "This is parameter 2: $2"
[test@szbirdora 1]$sh parm.sh a b
This is script name : parm.sh
This is parameter 1: a
This is parameter 2: b
● 向系统中传递位置变量
#!/bin/bash
#parm.sh
find /u01/test/1 -name $1 -print
[test@szbirdora 1]$ sh parm.sh myfile
/u01/test/1/myfile
● 标准变量
EXINIT
HOME
IFS
LOGNAME
MAIL
MAILPATH
PATH
TERM
TZ
PS1
[test@szbirdora 1]$ echo $PS1
[/u@/h /W]/$
PS2
PWD
MAILCHECK
[test@szbirdora 1]$ echo$MAILCHECK
60
SHELL
MANPATH
TERMINFO
● 特殊变量
$#
$*
$$
$!
$@
$-
$?
eg.
#!/bin/bash
#parm
echo "this is shellname: $0"
echo "this is parm1 :
echo "this is parm2 :
echo "show parm number : $#"
echo "show parm list :
echo "show process id:
echo "show precomm stat: $?"
[test@szbirdora1]$ sh parm.sh a b
this is shellname: parm.sh
this is parm1 :
this is parm2 :
show parm number : 2
show parm list :
show process id:
show precomm stat: 0
● 影响变量的命令
declare 设置或显示变量
export
shift[n]
typeset
注意: 双引号不能解析$,/,` 三个字符,所以在双引号中可以引用变量、转义字符、替换变量
单引号可以解析,所以单引号中引用变量等无效
[test@szbirdora 1]$ echo"$test"
test
[test@szbirdora 1]$ echo '$test'
$test
● 运算符类型
⒈ 按位运算符
~
<<
>>
&
|
^
$[ ]
2. 逻辑运算符
&&
||
>,<,=,!=
3. 赋值运算符
let variablename1 +=variablename1+ varablename2
第三章 shell 的输入和输出
1. echo
#!/bin/bash
#echo
echo -e "this echo's 3 newlne/n/n/n"
echo "OK"
echo
echo "this is echo's 3 ewline/n/n/n"
echo "this log file have all beendone">mylogfile.txt
[test@szbirdora ~]$ sh echod.sh
this echo's 3 newlne
OK
thisis echo's 3 ewline/n/n/n
上面可以看到有-e 则可以解析转移字符,没有不能解析。echo 空输出为空
2. read 可以从键盘或文件的某一行文本中读入信息,并将其赋给一个变量
read variable1 variable2
eg.
#!/bin/bash
#readname
echo -n "first name:"
read firstname
echo -n "last name:"
read lastname
echo "this name is $firstname $lastname"
3. cat
4. 管道|
5. tee
eg.
[test@szbirdora 1]$ echo |tee myfile
[test@szbirdora 1]$ cat myfile
将myfile 文件置空
6. 文件重定向
command>filename
command>>filename
command>filename>&1
command<<delimiter
command<filename
command<-
>nullfile.txt
command1<filename>command3
eg.
说明:myfile 为空间
[test@szbirdora 1]$df -lh>myfile
[test@szbirdora 1]$ cat myfile
Filesystem
/dev/sda1
none
/dev/sda2
/dev/sda4
[test@szbirdora 1]$ df-lh>myfile
[test@szbirdora 1]$ cat myfile
Filesystem
/dev/sda1
none
/dev/sda2
/dev/sda4
[test@szbirdora 1]$ df-lh>>myfile
[test@szbirdora 1]$ cat myfile
Filesystem
/dev/sda1
none
/dev/sda2
/dev/sda4
Filesystem
/dev/sda1
none
/dev/sda2
/dev/sda4
[test@szbirdora 1]$ cat>>myfile<<exit
> China
> Hubei
> Suizhou
> exit
[test@szbirdora 1]$ cat myfile
China
Hubei
Suizhou
7 . exec
第四章控制流结构
1.if语句
if 条件 1
then
elif 条件2
then
else
fi
------------------
if 条件
then 命令
fi
eg :
#!/bin/bash
#if test
#this is a comment line
if [ "10" -lt "12" ];then
#yes 10 is less than 12
echo "yes,10 is less than 12"
else
echo "no"
fi
注意: if 语句必须以 fi 终止
条件表达式中的比较函数
man test
NAME
SYNOPSIS
DESCRIPTION
eg.
#!/bin/bash
#if test
#this is a comment line
echo "Enter your filename:"
read myfile
if [ -e $myfile ]
then
else
echo "file no exist"
fi
[test@szbirdora 1]$ sh iftest.sh
Enter your filename:
11
11 exist but size is zero
2.case 语句
case 语句为多选择语句。
case 值in
模式1 )
模式2)
esac
eg.
#!/bin/bash
#case select
echo -n "enter a number from 1 to 3:"
read ans
case $ans in
1)
echo "you select 1"
;;
2)
echo "you select 2"
;;
3)
echo "you select 3"
;;
*)
echo "`basename $0`:this is not between 1 and3">&2
exit;
;;
esac
3.for 循环
for 循环一般格式:
for 变量名in 列表 ( 列表以空格作为分割)
do
done
eg :
#!/bin/bash
#forlist1
for loop in 1 2 3 4 5
do
echo $loop
done
4.until 循环
until 条件
do
done
条件测试发生在循环末尾,所以循环至少可以执行一次。
5.
while 循环
while 命令 (可以是一个命令也可以是多个,做条件测试)
do
done
注意:如果从文件中读入变量<filename 要放到done 后
6.break 和continue 控制
break 跳出,continue 跳过
第五章文本过滤
1. 正则表达式
一种用来描述文本模式的特殊语法,由普通字符以及特殊字符(元字符)组成
^
$
*
[]
/
.
pattern/{n/}只用来匹配前面pattern出现的次数,n 为次数
pattern/{n ,/}只用来匹配前面pattern出现的次数,至少为n
pattern/{n ,m/} 只用来匹配前面pattern 出现的次数,次数在n-m 之间
eg:
A/{3/}B
A/{3,/}B AAAB AAAAB ...
A/{3,5/}B AAAB AAAAB AAAAAB
2.find命令
findpathname -options [-print -exec -ok]
pathname -- 查找的目录路径. .-- 表示当前目录,/ 表示根目录
-print 输出
-exec 对匹配的文件执行该参数所给出的shell 命令,相应命令形式为'command'{}/;'
-ok
options
-name
-perm
-user
-group
-mtime -n +n (atime,-ctime) 修改时间(访问时间,创建时间)
-size n[c]
-type 查找某一类型的文件
eg.
[test@szbirdora 1]$ find ./ -mtime+5
./helloworld.sh
./nohup.out
查看./目录(当前)下修改时间超过5天的文件
3.grep 介绍
grep -c 输出匹配行计数
grep -i 不区分大小写
grep -h 查询多文件时不显示文件名
grep -H 显示文件名
grep -l 查询多文件时只输出包含匹配字符的文件名
grep -n 显示匹配行及行号
grep -s 不显示不存在或不匹配文本的错误信息
grep -v 显示不包含匹配文本的所有行(过滤文本)
eg.
[test@szbirdora 1]$ grep -n 's.a' myfile
2:/dev/sda1
4:/dev/sda2
5:/dev/sda4
[test@szbirdora 1]$ grep -n '2$' myfile
5:/dev/sda4
grep -options ' 正则表达式'filename
4.sed 介绍
sed 不与初始化文件打交道,它操作的只是一个拷贝,然后所有的改动如果没有重定向到一个文件将输出到屏幕
sed 是一种重要的文本过滤工具,使用一行命令或使用管道与grep 与awk相结合。
sed 调用:
1. 命令 sed [options] ' 正则表达式sedcommand'input-files
2.script : sed [options] -fsedscript input-files
sed在文本中查询文本的方式
x ---- 行号
x,y ---- 行号范围从x到y
x,y! --- 不包含行号x到y
sed命令选项:
-n 不打印
-c 下一个命令是编辑命令
-f 如果正在调用sed脚本文件
基本sed 命令
p 打印匹配行
= 显示文本行号
a/ 在定位行号后附加新文本信息
i/ 在定位行号前插入新文本信息
d 删除定位行
c/ 用新文本替换定位文本
s 使用替换模式替换相应模式
r 从另一个文件中读文本
w 写文本到一个文件
q 第一个模式匹配完成后退去
l 显示与八进制ascii代码等价的控制字符
{} 在定位行执行命令组
n 从一个文件中读文本下一行,并附加在下一行
g 将模式2粘贴到/pattern n/
y 传送字符
eg.
[test@szbirdora 1]$ sed -n '2p' myfile
c
打印myfile 第2 行
[test@szbirdora 1]$ sed -n '2,4p' myfile
c
f
b
打印第二行到第四行
[test@szbirdora 1]$ sed -n '/a/p' myfile
a
打印匹配a 的行
[test@szbirdora 1]$ sed -n '2,/2/p'myfile
c
f
b
1
2
打印第二行到匹配'2' 的行
s命令替换
[test@szbirdora 1]$ sed 's/b/a/p' myfile
a
a
a
c
d
e
替换b 为a
多点编辑 -e
eg.(myfile 包含a-e )
[test@szbirdora 1]$ sed -e '2d' -e 's/c/d/' myfile11
a
d
d
e
sed命令r ---从文件中读取选定的行,读入输入文件中,显示在匹配的行后面
eg.
[test@szbirdora 1]$ cat 11
*******************Alaska***************
[test@szbirdora 1]$ sed '/a/r 11' myfile
a
*******************Alaska***************
b
c
d
e
写入命令:w
eg.
[test@szbirdora 1]$ cat 11
b
[test@szbirdora 1]$ sed -n '/a/w 11' myfile
[test@szbirdora 1]$ cat 11
a
追加:a
eg.
[test@szbirdora 1]$ sed '/b/a-------------china---------'myfile
a
b
****************hello*************-------------china---------
c
d
e
插入命令:i
eg.
[test@szbirdora 1]$ sed '/b/i/
> THE CHARACTER B IS BEST/
> *******************************' myfile
a
THE CHARACTER B IS BEST
*******************************
b
c
d
e
下一个:n 从一个文件中读文本下一行,并附加在下一行
退出命令 q打印多少行后退出
eg.
[test@szbirdora 1]$ sed '3q' myfile
a alert
b best
c cook
sed script:
sed -f scriptfile myfile
5.awk 介绍
awk 可从文件或字符串值基于指定规则浏览和抽取信息
awk 三种调用方式:
1. 命令行方式
awk [-F field-sperator]'pattern{active}'input-files
awk [-F field-sperator]'command' input-files
awk 脚本
所有awk 命令插入一个文件,并使awk 程序可执行,然后用awk 命令解析器作为脚本的首行,以便通过键入脚本名称来调用。
awk 命令插入一个单独文件
awk -f awk-script-file input-files
awk脚本由模式和动作组成
分隔符、域、记录
注意这里的$1,$2 是域与位置变量$1,$2 不一样。$0 文件中的所有记录
eg:
awk '{print $0}' myfile
awk 'BEGIN {print "IP DATE ----"}{print $1"/t"$4}END{print "end-of-report"}
[test@szbirdora 1]$ df |awk '$1!~"dev"'|grep -v Filesystem
none
[test@szbirdora 1]$ df |awk '{if ($1=="/dev/sda1") print $0}'
/dev/sda1
[test@szbirdora shelltest]$ cat employee
TomJones
MaryAdams
SallyChang
BillyBlack
[test@szbirdora shelltest]$ awk '/[Aa]dams/'employee
MaryAdams
[test@szbirdora shelltest]$ sed -n '/[Aa]dams/p'employee
MaryAdams
[test@szbirdora shelltest]$ grep '[Aa]dams'employee
MaryAdams
三种命令方式下,使用模式匹配查询
[test@szbirdora shelltest]$ awk '{print $1}'employee
Tom
Mary
Sally
Billy
打印文件第一列
[test@szbirdora shelltest]$ awk '/Sally/{print$1"/t"$2}' employee
Sally
打印匹配Sally 的行的第一列和第二列
[test@szbirdora shelltest]$ df |awk'$4>20884623'
Filesystem
/dev/sda2
/dev/sda4
打印df 输出第四列大于×× 的行
格式输出:
打印函数—
[test@szbirdora shelltest]$ date
Mon Mar 10 15:15:47 CST 2008
[test@szbirdora shelltest]$ date |awk '{print "Month:" $2"/nYear:"$6}'
Month:Mar
Year:2008
[test@szbirdora shelltest]$ awk '/Sally/{print "/t/tHave a niceday,"$1"/t"$2}' employee
printf函数
[test@szbirdora shelltest]$ echo "LINUX"|awk'{printf "|%-10s|/n",$1}'
|LINUX
[test@szbirdora shelltest]$ echo "LINUX"|awk '{printf"|s|/n",$1}'
|
~匹配符
[test@szbirdora shelltest]$ awk '$1~/Tom/{print$1,$2}' employee
Tom Jones
awk给表达式赋值
关系运算符:
<
>
==
!=
>=
<=
~
!~
eg.
[test@szbirdora shelltest]$ cat employee
TomJones
MaryAdams
SallyChang
BillyBlack
[test@szbirdora shelltest]$ awk '$2~/Adams/' employee
MaryAdams
条件表达式:
condition
eg.
awk '{max=($1>$2) ? $1:$2;printmax}' filename
运算符
+ ,- ,* ,/,%,^,&&,||,!
[test@szbirdora shelltest]$ cat /etc/passwd |awk-F: '/
NF!=7{/
printf("line %d does not have 7 fields:%s/n",NR,$0)}/
$1!~/[A-Za-z0-9]/{printf("line %d,nonalphanumberic userid:%s/n",NR,$0)}/
$2=="*"{printf("line %d,no password:%s/n",NR,$0)}'
awk编程
递增操作符 x++ ,++x
递减操作符 x-- ,--x
BEGIN 模块
BEGIN 模块后面紧跟着动作块,在读入文件前执行。通常被用来改变内建变量的值,如:FS/RS/OFS, 初始化变量的值和打印输出标题。
[test@szbirdora shelltest]$ awk 'BEGIN{print"HELLO WORLD"}'
HELLO WORLD
[test@szbirdora shelltest]$ awk 'BEGIN{print"---------LIST---------"}{print}END{print "------END--------"}'donors
---------LIST---------
Mike Harrington:(510) 548-1278:250:100:175
Christian Dobbins:(408) 538-2358:155:90:201
Susan Dalsass:(206) 654-6279:250:60:50
Archie McNichol:(206) 548-1348:250:100:175
Jody Savage:(206) 548-1278:15:188:150
Guy Quigley:(916) 343-6410:250:100:175
Dan Savage:(406) 298-7744:450:300:275
Nancy McNeil:(206) 548-1278:250:80:75
John Goldenrod:(916) 348-4278:250:100:175
Chet Main:(510) 548-5258:50:95:135
Tom Savage:(408) 926-3456:250:168:200
Elizabeth Stachelin:(916) 440-1763:175:75:300
------END--------
重定向和管道
输出重定向
awk 输出重定向到一个文件需要使用输出重定向符,输出文件名需要用双引号括起来。
[test@szbirdora shelltest]$awk -F: '{print $1,$2>"note"}'donors
[test@szbirdora shelltest]$ cat note
Mike Harrington (510) 548-1278
Christian Dobbins (408) 538-2358
Susan Dalsass (206) 654-6279
Archie McNichol (206) 548-1348
Jody Savage (206) 548-1278
Guy Quigley (916) 343-6410
Dan Savage (406) 298-7744
Nancy McNeil (206) 548-1278
John Goldenrod (916) 348-4278
Chet Main (510) 548-5258
Tom Savage (408) 926-3456
Elizabeth Stachelin (916) 440-1763
输入重定向
getline 函数
[test@szbirdora shelltest]$ awk 'BEGIN{"date+%Y"|getline d;print d}'
2008
[test@szbirdora shelltest]$ awk -F"[ :]" 'BEGIN{printf "What is yourname?";/
getline name<"/dev/tty"}/
$1~ name{print "Found/t" name "/ton line",NR"."}/
END{print "see ya," name "."}' donors
What is your name?Jody
Found
see ya,Jody.
[test@szbirdora shelltest]$ awk'BEGIN{while(getline<"/etc/passwd">0)lc++;printlc}'
36
从文件中输入,如果得到一个记录,getline 函数就返回1 ,如果文件已经到了末尾,则返回0 ,如果文件名错误则返回-1.
管道:
awk 命令打开一个管道后要打开下一个管道需要关闭前一个管道,管道符右边可以使用“” 关闭管道。在同一时间只有一个管道存在
[test@szbirdora shelltest]$ awk '{print$1,$2|"sort -r +1 -2 +0 -1"}' names
tony tram
john smith
dan savage
john oldenrod
barbara nguyen
elizabeth lone
susan goldberg
george goldberg
eliza goldberg
alice cheba
|后用"" 关闭管道
system 函数
system ("LINUXcommand" )
system("cat" $1)
system("clear")
条件语句
1.if (){}
2.if(){}
else{}
3.if(){}
else if(){}
else if(){}
else{}
[test@szbirdora shelltest]$ awk -F: '{if($3>250){printf "%-2ss/n",$1,"-----------goodpartman"}else{print $1}}' donors
循环语句
[test@szbirdora shelltest]$ awk -F:'{i=1;while(i<=NF){print NF,$i;i++}}' donors
循环控制语句break 、continue
程序控制语句
next 从输入文件中读取下一行,然后从头开始执行awk 脚本
{if($1~/Peter/){next}
else{print}}
exit结束awk 语句,但不会结束END 模块的处理。
数组:
awk'{name[x++]=$1;for(i=0;i<NR;i++){print i,name[i]}}'donors
(P177)---2008.3.11
awk 内建函数
sub (正则表达式,替换字符[,$n] )--- 域n 匹配正则表达式的字符串将被替换。
[test@szbirdora shelltest]$ awk'{sub(/Tom/,"Jack",$1);print}' employee
Jack Jones 4424 5/12/66 543354
MaryAdams
SallyChang
BillyBlack
Jack He 3000 8/22/44 320000
index函数index (字符串,子字符串)子字符串在字符串中的位置
[test@szbirdora shelltest]$ awk'BEGIN{a=index("hello","llo");print a}'
3
length函数length (string ) 字符串的长度
[test@szbirdora shelltest]$ awk'BEGIN{a=length("hello world");print a}'
11
substr函数substr (字符串,开始位置[ ,子字符串长度] )
[test@szbirdora shelltest]$ awk'BEGIN{a=substr("hello world",7);print a}'
world
[test@szbirdora shelltest]$ awk 'BEGIN{a=substr("helloworld",7,3);print a}'
wor
match(string, 正则表达式) 找出字符串中第一个匹配正则表达式的位置, 其内建变量RSTART 为匹配开始位置,RLENGTH 为匹配开始后字符数
[test@szbirdora shelltest]$ awk'{a=match($0,/Jon/);if (a!=0){print NR,a}}' employee
1 5
[test@szbirdora shelltest]$ awk '{a=match($0,/Jon/);if (a!=0){printNR,a,RSTART,RLENGTH}}' employee
1 5 5 3
toupper和tolower 函数
[test@szbirdora shelltest]$ awk'BEGIN{a=toupper("hello");print a}'
HELLO
split函数split (string,array,fieldseperator )
[test@szbirdora shelltest]$ awk 'BEGIN{"date"|getlined;split(d,date);print date[2]}'
Mar
时间函数
systime () ----1970年1月1日到当前忽略闰年得出的秒数。
strftime( 格式描述,时间戳)
[test@szbirdora shelltest]$ awk'BEGIN{d=strftime("%T",systime());print d}'
13:08:09
[test@szbirdora shelltest]$ awk'BEGIN{d=strftime("%D",systime());print d}'
03/12/08
[test@szbirdora shelltest]$ awk'BEGIN{d=strftime("%Y",systime());print d}'
2008
6.sort 介绍
sort:
[test@szbirdora 1]$ df -lh|grep -v'Filesystem'|sort +1
none
/dev/sda1
/dev/sda4
/dev/sda2
uniq [option]files从一个文本文件中去除或禁止重复行
注意要先排序
7.split cut join分割和合并文件命令
[test@szbirdora 1]$ split -l 2 myfilesplit
[test@szbirdora 1]$ ls
case.sh df.out helloworld.sh iftest.sh myfile nohup.outnullfile.txt parm.sh splitaa splitab splitac splitad splitae
[test@szbirdora 1]$ cat splitaa
Filesystem
/dev/sda1
第六章 shell 函数
1. 定义函数
funcation name()
{
}
或
函数名()
eg.
#!/bin/bash
#hellofun
function hello()
{
echo "hello,today is `date`"
return 1
}
2. 函数调用
#!/bin/bash
#hellofun
function hello()
{
echo "hello,today is `date`"
return 1
}
echo "now going to the function hello"
hello
echo "back from the function"
所以调用函数只需要在脚本中使用函数名就可以了。
3. 参数传递
像函数传递参数就像在脚本中使用位置变量$1,$2...$9
4. 函数文件
函数可以文件保存。在调用时使用". 函数文件名"(.+ 空格+ 函数文件名)
如:
hellofun.sh
#!/bin/bash
#hellofun
function hello()
{
echo "hello,today is `date`"
return 1
}
func.sh
#!/bin/bash
#func
. hellofun.sh
echo "now going to the function hello"
echo "Enter yourname:"
read name
hello $name
echo "back from the function"
[test@szbirdora 1]$ sh func.sh
now going to the function hello
Enter yourname:
hh
hello,hh today is Thu Mar 6 15:59:38 CST 2008
back from the function
5. 检查载入函数 set
删除载入函数 unset 函数名
6. 函数返回状态值return 0 、return 1
7. 脚本参数的传递
shift 命令
shift n 每次将参数位置向左偏移n
#!/bin/bash
#opt2
usage()
{
echo "usage:`basename $0` filename"
}
totalline=0
if [ $# -lt 2 ];then
fi
while [$# -ne 0]
do
done
echo "-----"
echo "total:${totalline}"
[test@szbirdora 1]$ sh opt2.sh myfile df.out
myfile : 10
df.out : 4
-----
total:14
8.getopts 命令
获得多个命令行参数
getopts ahfvc OPTION
该命令可以做获得命令的参数
#!/bin/bash
#optgets
ALL=false
HELP=false
FILE=false
while getopts ahf OPTION
do
done
ALL is true
HELP is true
optgets.sh: illegal option -- m
optgets.sh -[a h f] file
getopts 表达式:
while getopts p1p2p3... var
done
如果在参数后面还需要跟自己的参数,则需要在参数后加:
如果在参数前面加:表示不想将错误输出
getopts 函数自带两个跟踪参数的变量:optind ,optarg
optind 初始值为1,在optgets处理完一次命令行参数后加1
optarg 包含合法参数的值,即带:的参数后跟的参数值
前七章的部分知识在前面的linuxshell学习笔记中已经结合进去了。所以笔记从第八章开始。而且这本书的目录编排也是这样,第八章才开始正式涉及shell编程。
有了前面的学习,下面只记载一些在学习的过程中又忘了了一些知识点。所以记录是零散的。
1.
shopt bash2.0以上新的命令,功能和set类似。
给变量赋值时等号两边不可留空格。
环境变量一般使用大写。
2.
$# 传递到脚本的参数个数
$* 以一个单字符串显示所有向脚本传递的参数,与位置变量不同,参数可超过9个
$$ 脚本运行的当前进程ID号
$! 后台运行的最后一个进程的进程ID号
$@ 传递到脚本的参数列表,并在引号中返回每个参数
$- 显示shell使用的当前选项,与set命令功能相同
$? 显示最后命令的退出状态,0表示没有错误,其他表示有错误
3.
echo 命令中使用" "无法直接识别转义字符,必须使用选项 -e,但可以使用$和`引用变量和命令替换。
$[] 告诉shell对方括号中表达式求值 $[a+b],如$[1+8]
4.
tee
把输出的一个副本输送到标准输出,另一个副本拷贝到相应的文件中
tee -afile
该命令一般与管道合用
5.
command>filename>&1---把标准输出和标准错误重定向
command<<delimiter---输入直到delimiter分解符
eg:
sqlplus / as sysdba <<EOF
show parameters
exit
EOF
6.命令替换有两种方式,老的korn风格的`linux command`和新的bash风格$(linux command)
7.定义数组
declare -a arry=(a1 a2 a3 ...)
echo ${a[n]}
8.read使用
read -aarryname
read -pprompt
[test@szbirdora 1]$ read -p "Enter your name:"
Enter your name:jack
[test@szbirdora 1]$ echo $REPLY
jack
[test@szbirdora 1]$ read -a name
jack tom susan
[test@szbirdora 1]$ echo ${name[2]}
susan
[test@szbirdora 1]$ echo ${name[0]}
jack
9.多进制整型变量表示
declare -i number
number=base#number_in_the_base
如:
declare -i number
number=2#101
number=16#A9
10.条件语句if thenfi中if后的表达式可以是条件表达式(布尔表达式)或一组命令,如果是布尔表达式则表达式为真执行then后的语句,如果是命令组,则命令组状态($?)为0执行then后面的语句。但如果是Cshell则if后只能跟布尔表达式。
11.here文档和case建立菜单:
eg.
echo "Select a terminal type:"
cat <<EOF
1) linux
2)xterm
3)sun
EOF
read choice
case $choice in
1)TERM=linux
2)TERM=xterm
;;
3)TERM=sun
;;
*) echo "please select correct chioce,ths!"
;;
esac
echo "TERM is $TERM"
12.循环比较:
for variable inwordlist;do
whilecommand;do
untilcommand;do
select循环菜单
用select建立菜单,需要用PS3来提示用户输入,输入保存在REPLY内建变量中,REPLY的值与内建菜单关联。在构建菜单过程中可以使用COLUMNS和LINES两个变量,COLUMNS决定菜单的列宽度,LINES决定可显示的行数。select和case命令联用可以有效的构造循环菜单。
eg
#!/bin/bash
#Author: hijack
#Usage:Menu
t=0
j=0
d=0
PS3="Please choose one of the three boys or quit:"
select choice in Tom Jack David Quit
do
case $choice in
Tom)
t=$t+1
if (($t==5));then
echo "Tom win"
break
fi
;;
Jack)
j=$j+1
if (($j==5));then
echo "Jack win"
break
fi
;;
David)
d=$d+1
if (($d==5));then
echo "David win"
break
fi
;;
Quit) exit 0;;
*) echo "$REPLY is invalide choice"1>&2
;;
esac
done
[test@szbirdora 1]$ sh menu
1) Tom
2) Jack
3) David
4) Quit
Please choose one of the three boys or quit:1
Please choose one of the three boys or quit:2
Please choose one of the three boys or quit:1
Please choose one of the three boys or quit:1
Please choose one of the three boys or quit:1
Please choose one of the three boys or quit:1
Tom win
set tom jack david -----$1 tom $2 jack $3 david
echo $*
tom jack david
shift2
echo $*
david
eg:
#!/bin/bash
#Name:shift
#Author : Hijack
#Usage:shift test
#Date:080320
while (($#>0))
do
done
[test@szbirdora 1]$ ./shift 1 2 3 4 5 6 7
1 2 3 4 5 6 7
2 3 4 5 6 7
3 4 5 6 7
4 5 6 7
5 6 7
6 7
7
13。 break n
#!/bin/bash
#Name
#Author : Hijack
#Usage : break test
declare -i x=0
declare -i y=0
while true
do
while (( x<20 ))
do
done
echo "loop end"
y=$y+1
if (($y>5));then
fi
done
[test@szbirdora 1]$ sh mulloop
1
2
3
4
5
6
7
8
9
10
if
loop end
11
12
13
14
15
16
17
18
19
20
loop end
loop end
loop end
loop end
loop end
#!/bin/bash
#Name
#Author : Hijack
#Usage : break test
declare -i x=0
declare -i y=0
while true
do
while (( x<20 ))
do
done
echo "loop end"
y=$y+1
if (($y>5));then
fi
done
[test@szbirdora 1]$ sh mulloop
1
2
3
4
5
6
7
8
9
10
if
14.循环的IO重定向
使用">","|"等重定向符实现循环的IO重定向
如 while ;do
eg
给文件的每行加一个行号,写入文件中
#!/bin/bash
#Name
#Author : Hijack
#Usage
#Program : read line to loop from file,add linenum,output totempfile,mv tempfile to file
declare -i count=0
declare -i total=0
total=`sed -n "$=" $1`
cat $1 | while read line
do
done >temp$$
mv temp$$ $1
[test@szbirdora 1]$ sh loopred testmv
Processing file testmv.....
Process finish,total line number is 19
[test@szbirdora 1]$ vi testmv
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
15。在done后面加&使循环在后台运行,程序继续执行。
16.在函数内可以使用local定义本地变量,local variable。
17.陷阱信号 trap --当一个信号发出传递给进程时,进程进行相关操作,信号包括中断等
eg:
[root@linux2 ~]# trap "echo -e 'helloworld/n';ls -lh" 2
[root@linux2 ~]# helloworld
total 100K
-rw-r--r-- 1 root root 1.4K Nov 14 16:53 anaconda-ks.cfg
drwxr-xr-x 2 root root 4.0K Nov 23 13:11 Desktop
-rw-r--r-- 1 root root 53K Nov 14 16:53 install.log
-rw-r--r-- 1 root root 4.9K Nov 14 16:53 install.log.syslog
drwxr-xr-x 2 root root 4.0K Nov 22 13:03 vmware
附:
shell 字符串处理汇总(查找,替换等等)
Shell中的数组