shell脚本语法

来源:互联网 发布:课堂教学互动软件 编辑:程序博客网 时间:2024/05/16 02:04
bash变量类型:环境变量,本地变量,局部变量,位置变量,特殊变量环境变量: 作用域为当前shell及其子进程export VARNAME=VALUE或VARNAME=VALUEexport VARNAME本地变量: 作用域为当前shell进程 set VARNAME=VALUE局部变量: 作用域为当前代码段local VARNAME=VALUE位置变量: 用于引用参数$1,$2,$3...shift特殊变量: 用于保存特殊数据$?: 保存上一个命令执行状态返回值$#: 参数的个数$*: 参数列表$@: 参数列表成功执行两个返回值:执行结果: 执行状态(0-255): 正确执行为0,执行错误为1-255,其中1,2,127系统预留 输出重定向:> : 覆盖重定向>>: 追加重定向2>: 错误重定向2>>: 错误追加重定向&>: 同时重定向/dev/null: 软件设备, bit bucket撤销变量:unset VARNAME查看变量:set 查看当前shell中的环境变量:printenvenvexportbash中如何实现条件判断?条件测试类型:整数测试字符测试文件测试条件测试的表达式:[ expression ]: 命令测试法,表达式两边一定要有空格[[ expression ]]: 关键字测试法test expression整数测试:-eq: 测试两个整数是否相等; (e.g)[ $A -eq $B ]-ne: 测试两个整数是否不等;-gt: 测试两个整数是否大于关系-lt: 测试两个整数是否小于关系-ge: 大于或等于-le:小于或等于字符集合:[:digit:], [:lower:], [:upper:], [:punct:], [:space:], [:alpha:], [:alnum:]字符测试:==或=: =两边要有空格,不然会被识别为赋值 A=hello B=hi(e,g) [ $A = $B ]!=: 测试是否不相等><-n string: 测试指定字符串是否为空-s string: 测试指定字符串是否不空文件测试:-e FILE: 测试文件是否存在,  (e.g)[ -e /etc/inittab ]-f FILE: 测试文件是否为普通文件-d FILE: 测试指定路径是否为目录-r FILE: 测试对当前用户指定文件是否有读权限-w FILE: 测试对当前用户指定文件是否有写权限-x FILE: 测试对当前用户指定文件是否有执行取权限bash 技巧bash -n xxx.sh 检查脚本语法bash -x xxx.sh 检查脚本执行了哪些语句脚本在执行时会启动一个子shell进程:命令行中启动的脚本会继承当前shell环境变量系统自动执行的脚本(非命令行启动)就需要自我定义需要各环境变量命令的间逻辑关系:    逻辑与: &&        第一个条件为假时,第二条件不用再判断,最终结果已经有;        第一个条件为真时,第二条件必须得判断;    逻辑或: ||如果用户user6不存在,就添加用户user6! id user6 && useradd user6id user6 || useradd user6如果/etc/inittab文件的行数大于100,就显示好大的文件;[ `wc -l /etc/inittab | cut -d' ' -f1` -gt 100 ] && echo "Large file."变量名称:    1、只能包含字母、数字和下划线,并且不能数字开头;    2、不应该跟系统中已有的环境变量重名;    3、最好做到见名知义;如果用户存在,就显示用户已存在;否则,就添加此用户;id user1 && echo "user1 exists." || useradd user1如果用户不存在,就添加;否则,显示其已经存在;! id user1 && useradd user1 || echo "user1 exists."如果用户不存在,添加并且给密码;否则,显示其已经存在;! id user1 && useradd user1 && echo "user1" | passwd --stdin user1  || echo "user1 exists."一,条件控制###单分支的if语句if 判断条件;then    statement1    statement2      ...if###双分支的if语句if 判断条件; then    statement1    statement2      ...else    statement3    statement4      ...fi###多分支if语句if 判断条件1; then  statement1  ...elif 判断条件2; then  statement2  ...elif 判断条件3; then  statement3  ...else  statement4  ...fi###case语句:选择结构case SWITCH in value1)  statement ...  ;;value2)  statement  ...  ;;*)  statement  ...  ;;esaca-zA-Z0-9[abc]二,循环控制###Shell风格--for循环for 变量 in 列表;do    循环体donefor I in 1 2 3 4 ; do    循环体done生成for循环的列表括号法生成法:  {1..100} seq生成法:   `seq [起始数  [步进]]  结束数`declare -i SUM=0for I in {1..100};do    SUM=$[ $SUM+$I ]doneecho "The SUM is: $SUM"###C语言风格--for循环for (( expr1 ; expr2 ; expr3 )); do   循环体donedeclare  -i SUM=0for ((J=1;J<100;J++));do    let SUM+=$Jdone###while循环while循环:适用于循环次数未知的场景,要有退出条件语法:    while CONDITION; do      statement      ...    done###until循环进入循环:条件不满足退出循环:条件满足until CONDITION;do    statement    ...done    shell中进行算术运算1,let算数表达式A=3 B=6let C=$A+$Becho $C2,$[算术表达式]D=$[$A+$B]echo $D3,$((算术表达式))E=$(($A+$B))echo $E4,expr 算数表达式,表达式中各操作数及运算符之间要有空格,而且要用命令引用F=`expr $A+$B`echo $F脚本练习:shell中的计算保留精度result=`echo "scale=2;111/22;" | bc` echo $resultbc <<< "scale=2;111/22;"组合测试条件    -a: 与关系    -o: 或关系    !: 非关系if [ $# -gt 1 -a $# -le 3 ]if [ $# -gt 1 ] && [ $# -le 3 ]脚本练习:判断当前主机的CPU生产商,其信息在/proc/cpuinfo文件中vendor id一行中。如果其生产商为AuthenticAMD,就显示其为AMD公司;如果其生产商为GenuineIntel,就显示其为Intel公司;否则,就说其为非主流公司;#!/bin/bash#cpu=`grep "vendor_id" /proc/cpuinfo | sed -r 's@[[:space:]]*@@g' | cut -d: -f2`if [ "$cpu" = "AuthenticAMD" ];then    echo "Your CPU is AMD."elif [ "$cpu" = "GenuineIntel" ];then    echo "Your CPU is Intel."else     echo "Your CPU is UNKNOWN."fi脚本练习:1、设定变量FILE的值为/etc/passwd,依次向/etc/passwd中的每个用户问好,并显示对方的shell,   形如:Hello, root, your shell: /bin/bash   并统计一共有多少个用户#!/bin/bash#declare -i COUNT=0FILE="/etc/passwd"LINES=`wc -l /etc/passwd | cut -d' ' -f1`for I in `seq 1 $LINES` ;do    UserName=`head -n $I $FILE | tail -n 1 | cut -d: -f1`    UserShell=`head -n $I $FILE| tail -n 1 | cut -d: -f7 |sed -r 's@^/.*/([^/]+)/?@\1@'`    echo "Hello, $UserName, your shell: $UserShell"    let COUNT=$COUNT+1doneecho "The Mount Of User is $COUNT. "2、添加10个用户user1到user10,密码同用户名;但要求只有用户不存在的情况下才能添加;接受一个参数:add: 添加用户user1..user10del: 删除用户user1..user10其它:退出#!/bin/bash#if [ $# -lt 1 -o `whoami | id -u` -ne 0 ];then    echo "Please use root execute this shell-script.Usage: adminusers.sh [--add or --del]"    exit 2fiif [ "$1" = "--add" ];then    for I in {1..10}; do        ( id -u "user$I" &> /dev/null  && echo "user$I is exist." ) || ( useradd  "user$I" &> /dev/null &&  echo  "user$I" | passwd --stdin "user$I" &> /dev/null && echo "Add "user$I" Successfully.")    doneelif [ "$1" = "--del" ];then    for I in {1..10}; do        ( userdel  -r "user$I" >& /dev/null && echo "Delete "user$I" Successfully.")    doneelse    echo "Unkown arg,try again."    exit 3fi

数组的定义  何为数组?学过计算机编程语言的同学都知道,数组的特性就是一组数据类型相同的集合(不包括有一些编程语言提出来的关联数组的概念)。那么shell中数组是怎么定义的呢,我们来看两种数据类型:一是数值类型,二是字符串类型;虽然shell本身是弱类型的,但也可以这么区分。  数值类型的数组:一对括号表示数组,数组中元素之间使用“空格”来隔开。  举个列子:   arr_number=(1 2 3 4 5);  字符串类型数组:同样,使用一对括号表示数组,其中数组中的元素使用双引号或者单引号包含,同样使用“空格”来隔开。  arr_string=("abc" "edf" "sss"); 或者 arr_string=('abc' 'edf' 'sss');数组的操作  我们使用数值类型数组arr_number=(1 2 3 4 5)做为源数组进行相关的讲解:获取数组长度,读取某个下标的值,对某个下标赋值,删除、分配和替换以及遍历。提一个知识点,我们在shell里面想获取某个变量的值,使用$符开头,如:$a或者${a}即可。  获取数组长度  arr_length=${#arr_number[*]}${#arr_number[@]}均可,即形式:${#数组名[@/*]} 可得到数组的长度。  读取某个下标的值  arr_index2=${arr_number[2]},即形式:${数组名[下标]}  对某个下标赋值  这里需要提出两个问题:    第一个问题是如果该下标元素已经存在,会怎么样?    答:会修改该下标的值为新的指定值。    例如:arr_number[2]=100,数组被修改为(1 2 100 4 5)    第二个问题是如果指定的下标已经超过当前数组的大小,如上述的arr_number的大小为5,指定下标为10或者11或者大于5的任意值会如何?    答:新赋的值被追加到数组的尾部。    例如:arr_number[13]=13,数组被修改为(1 2 100 4 5 13)  删除操作    清除某个元素:unset arr_number[1],这里清除下标为1的数组;    清空整个数组:unset arr_number;  分片访问    分片访问形式为:${数组名[@或*]:开始下标:结束下标},注意,不包括结束下标元素的值。    例如:${arr_number[@]:1:4},这里分片访问从下标为1开始,元素个数为4。  模式替换    形式为:${数组名[@或*]/模式/新值}    例如:${arr_number[@]/2/98}  数组的遍历    数组遍历我们使用for语句来演示:    for v in ${arr_number[@]}; do      echo $v;    done        另一个例子                #!/bin/bash                  declare -a serial                  serial=(1 2 3 4)                  PS3="Enter a number: "                  select var in "a" "b" "c" "d"                  do                      if ! echo ${serial[@]} | grep -q $REPLY; then                          echo "please enter [1-4]."                          continue                      fi                      echo "your anwser is: $var"                      break                  done  
0 0
原创粉丝点击