bash脚本编程
脚本文件格式:
第一行,顶格:#!/bin/bash
注释信息:#
代码注释:
缩进,适度添加空白行;
语言:编程语法格式,库,算法和数据结构
编程思想:
问题空间–解空间
变量:
局部变量
本地变量
环境变量
位置参数变量
特殊变量
数据类型:字符、数值型
弱类型:字符型
算术运算:
+ ,-, *, /,**
VAR= let VAR=$num1 op $num2
VAR= $[expression]
VAR=$((expression))
VAR=$(expr argu1 argu2 argu3)
注意:有些时候乘法符号需要转义;
增强型赋值:
变量做某种算术运算后回存至此变量中;
let i=$i+#
let i+=#
+=, -=, *=, %=
自增:
let VAR=$[$VAR+1]
let VAR+=1
let VAR++
自减:
VAR=$[VAR-1]
let VAR=1
let VAR–
练习:写一个脚本
1 计数/etc/passwd文件中的第10个用户和第20个用户的id号之和;
id1=$(head-10/etc/passwd | tail-1 | cut -d: -f3)
id1=$(head-20/etc/passwd | tail-1 | cut -d: -f3)
2、计算/etc/rc.d/init/d/functions和/etc/inittab文件的空白行数之和;
grep "^[[:space:]]*$" /etc/rc.d/init.d/functions | wc -l
条件测试:
判断某需求是否满足,需要由测试机制来实现;
如何编写测试表达式以实现所需的测试:
(1)执行命令,并利用命令状态返回值来判断;
0:成功
1-255:失败
(2)测试表达式
test EXPRESSION
[EXPRESSION]
[ [EXPRESSION]]
注意:EXPRESSION两端必须有空白字符,否则为语法错误;
bash的测试类型:
数值测试
字符串测试
文件测试
数值测试:数值比较
-eq: 是否等于: [$num1 -eq $num2]
-ne: 是否不等于;
-gt:是否大于等于;
-lt: 是否小于;
-le: 是否小于等于;
字符串测试:
==:是否等于;
>:是否大于;
<:是否小于;
!=:是否不等于;
=-: 左侧的字符串是否能够被右侧的PATTERN所匹配;
-z: "STRING":判断指定的字串是否为空;空位真,不空为假;
-n: "STRING":判断指定的字串是否为不空,不空为真,空则假;
注意:(1)字符串要加引号;
(2)要使用[[]];
文件测试:
存在性测试
-a FILE
-e FILE
文件的存在性测试,存在则为真,否则则为假;
存在性及类型测试
-b FILE: 是否存在并且为块设备文件;
-c:FILE :是否存在并且为目录文件;
-f: FILE 是否存在并且为普通文件;
-h: FILE 或 -L FILE: 是否存在并且为符号链接文件;
-p: FILE: 是否存在且为命名管道文件;
-s: FILE: 是否存在且为套接字文件;
文件权限测试:
-r FILE:是否存在并且对当前用户可读;
-w FILE:是否存在并且对当前用户可写;
-x FILE:是否存在并且对当前用户可执行;
特殊权限测试:
-u: FILE: 是否存在并且拥有suld权限;
-g: FILE 是否存在并且对当前用户可读;
-k FILE: 是否存在并且 拥有sticky 权限
;
文件是否有内容:
-s FILE: 是否有内容;
时间戳:
-N FILE: 文件自从上一次读操作后是否被修改过;
从属关系测试:
-O FILE:当前用户是否为文件的属主;
-G FILE: 当前用户是否属于文件的属组;
双目测试:
FILE1 -ef FILE2: FILE1与FILE2是否指向同一个文件系统相同inode的硬连接;
FILE1 -nt FILE2:FILE1是否新于FILE2;
FILE1 -ot FILE2: FILE1是否旧于FILE2;
组合测试条件:
逻辑运算:
第一种方式:
COMMAND1 && COMMAND2
COMMAND1 || COMMAND2
! COMMAND
[ -O FILE ] && [ -r FILE ]
第二种方式:
EXPRESSION1 -a EXPPRESSION2
! EXPRESSION
[ -O FILE -a -x FILE ]
练习:将当前主机名称保存至hostName变量中;
主机名如果为空,或者为localhost.localdomain,则将其设置为www.magedu.com;
hostName=&(hostname)
[ [ -z "$hostName" -o "$hostName"=="locahost.localdomain" -o "$hostName" == "localhost"]] && hostname www.magedu.com
脚本状态返回值:
默认是脚本中执行的最后一天命令的状态返回值;
自定义状态退出状态码:
exit [n]: n为自己指定的状态码;
注意:shell进程遇到exit时,即会终止,因此,整个脚本执行即 为结束;
向脚本传递参数:
位置参数变量
myscript.sh argu1 argu2
引用方式:
$1, $2,…,${10},${11},…
轮替:
shift [n]: 位置参数轮替;
练习;写一脚本,通过命令传递两个文本文件路径给脚本,计算器空白行数之和;
#!/bin/bash
#
file1-lines=$(grep "^$" $1 | wc -l)
file2-lines=$(grep "^$" $2 | wc -l)
echo "Total blank lines: $[$file1-lines+$file2-lines]"
特殊变量:
$0 :脚本文件路径的本身;
$#:脚本参数的个数;
$*: 所有参数;“hello" "hi" "toyou"
$@: 所有参数;"hello hi toyou"
过程式编程语言的代码执行顺序;
顺序执行:逐条运行;
选择执行:代码有一个分支:条件满足是才会执行;
两个或以上是分支:只会执行其中一个满足条件的分支;
循环执行:
代码片段(循环体)要执行0、1或多个来回;
选择执行:
if 测试条件
then
代码分支
fi
双分支的if语句;
if 测试条件;then
条件为真实执行的分支
else
fi
示例:通过参数传递一个用户给脚本,次用户不存在是,则添加之;
#!/bin/bash
#
if !|grep "^$1\“ /etc/passwd/ $> /dev/null; then
useradd $1
echo $1 | passwd –stdin $1 $> /dev/null
echo "Add user $1 finished."
fi
做条件判断:
#!/bin/bash
#
if [ $# -lt 1 ]; then
echo "At least one username."
exit 2
fi
if !|grep "^$1\“ /etc/passwd/ $> /dev/null; then
echo "User $1 exists."
else
useradd $1
echo $1 | passwd –stdin $1 $> /dev/null
echo "Add user $1 finished."
fi
练习1、通过命令行参数给定的两个数字,输出其中较大的数值;
第一种:
#!/bin/bash
#
if [ $# -lt 2 ]; then
echo "Two integers."
exit 2
fi
if [ $1 -ge $2 ]; then
echo "Max numeber: $1."
elese
echo "Max numeber: $2."
fi
第二种:
#!/bin/bash
#
if [ $# -lt 2 ]; then
echo "Two integers."
exit 2
fi
declare -i max=$1
if [ $1 -ge $2 ]; then
max=$1
else
max=$2
fi
echo "Max number: $max."
原创文章,作者:shadow,如若转载,请注明出处:http://www.178linux.com/64546