@yanglt7
2018-10-31T14:48:10.000000Z
字数 6866
阅读 759
Shell
1)变量取值型:
for 变量名 in 变量取值列表 #<== 变量名依次获取变量取值列表内容(以空格分隔),每次仅取一个docmd...done
2)C 语言型:
for((exp1; exp2; exp3))docmd...done
例 10-1 竖向打印 5、4、3、2、1 这 5 个数字。
#!/bin/bash#for n in 5 4 3 2 1 #<== 直接列出元素#for n in {5..1} #<== 利用大括号 {} 生成数字序列for n in `seq 5 -1 1` #<== 采用 seq 生成数字序列doecho "$n"done
例 10-2 获取当前目录下的目录或文件名,并将其作为变量列表打印输出。
#!/bin/bashfor filename in `ls`doecho "$filename"done
例 10-3 用 for 循环批量修改文件扩展名。
[root@web001 scripts]# ll test/total 0-rw-r--r-- 1 root root 0 Oct 26 12:47 test.gif-rw-r--r-- 1 root root 0 Oct 26 12:47 ylt.gif[root@web001 scripts]# cat 222.sh#!/bin/bashcd testfor filename in `ls|grep "gif$"`domv $filename `echo $filename|cut -d . -f1`.txtdone[root@web001 scripts]# sh 222.sh[root@web001 scripts]# ll test/total 0-rw-r--r-- 1 root root 0 Oct 26 12:47 test.txt-rw-r--r-- 1 root root 0 Oct 26 12:47 ylt.txt
法 2:通过 rename 命令实现[root@web001 test]# rename "txt" "gif" *.txt[root@web001 test]# lltotal 0-rw-r--r-- 1 root root 0 Oct 26 12:47 test.gif-rw-r--r-- 1 root root 0 Oct 26 12:47 ylt.gif
例 10-4 在 Linux 下批量修改文件名,将 “_finished” 去掉。
[root@web001 test]# lltotal 4-rw-r--r-- 1 root root 95 Oct 26 14:48 223.sh-rw-r--r-- 1 root root 0 Oct 26 14:44 test_1_finished.jpg-rw-r--r-- 1 root root 0 Oct 26 14:44 test_2_finished.jpg[root@web001 test]# cat 223.sh#!/bin/bashfor file in `ls *.jpg`domv $file `echo $file|sed 's/_finished//g'`#mv $file `echo "${file%_finished*}.jpg"`done[root@web001 test]# sh 223.sh[root@web001 test]# lltotal 4-rw-r--r-- 1 root root 99 Oct 26 14:49 223.sh-rw-r--r-- 1 root root 0 Oct 26 14:44 test_1.jpg-rw-r--r-- 1 root root 0 Oct 26 14:44 test_2.jpg
法 2:ls 结合 awk 实现
[root@web001 test]# lltotal 2-rw-r--r-- 1 root root 0 Oct 26 14:44 test_1.jpg-rw-r--r-- 1 root root 0 Oct 26 14:44 test_2.jpg[root@web001 test]# ls|awk -F "." '{print $0,$1,$2}'test_1.jpg test_1 jpgtest_2.jpg test_2 jpg[root@web001 test]# ls|awk -F "." '{print $0,$1"_finished."$2}'test_1.jpg test_1_finished.jpgtest_2.jpg test_2_finished.jpg[root@web001 test]# ls|awk -F "." '{print "mv",$0,$1"_finished."$2}'mv test_1.jpg test_1_finished.jpgmv test_2.jpg test_2_finished.jpg[root@web001 test]# ls|awk -F "." '{print "mv",$0,$1"_finished."$2}'|bash[root@web001 test]# lltotal 2-rw-r--r-- 1 root root 0 Oct 26 14:44 test_1_finished.jpg-rw-r--r-- 1 root root 0 Oct 26 14:44 test_2_finished.jpg
法 3:通过 rename 实现
[root@web001 test]# rename "_finished" "" *.jpg[root@web001 test]# ll-rw-r--r-- 1 root root 0 Oct 26 14:44 test_1.jpg-rw-r--r-- 1 root root 0 Oct 26 14:44 test_2.jpg
例 10-5 通过脚本实现仅 sshd、rsyslog、crond、network、sysstat 服务在开机时自启动。
root@web001 scripts]# for service in `systemctl list-unit-files|grep enabled|awk '{print $1}'`;do systemctl disable $service;doneroot@web001 scripts]# for service in crond network rsyslog sshd sysstat;do systemctl enable $service;done
for service in `systemctl list-unit-files|grep enabled|awk '{print $1}'|grep -vE "crond|network|sshd|rsyslog|sysstat"`;do systemctl $service disable;done
systemctl list-unit-files|grep enabled|grep -vE "crond|sshd|network|rsyslog|sysstat"|awk '{print "systemctl disable", $1}'|bashsystemctl list-unit-files|egrep -v "crond|sshd|network|rsyslog|sysstat"|awk '{print "systemctl disable", $1}'|bashsystemctl list-unit-files|grep enabled|grep -vE "crond|sshd|network|rsyslog|sysstat"|awk '{print $1}'|sed -r 's#(.*)#systemctl disble \1#g'|bash
例 10-6 打印九九乘法表。
#!/bin/bashCOLOR='\E[47;30m'RES='\E[0m'for num1 in `seq 9`dofor num2 in `seq 9`doif [ $num1 -ge $num2 ]; thenif ((num1*num2>9)); thenecho -en "${COLOR}${num2}*${num1}=$((num1*num2))$RES "elseecho -en "${COLOR}${num2}*${num1}=$((num1*num2))$RES "fifidoneecho " "done
例 10-7 实现 mysql 分库备份脚本
#!/bin/bashPATH="/application/mysql/bin:$PATH"DBPATH=/tmp/backupMYUSER=rootMYPASS=passwordSOCKET="/data/3306/mysql.sock"MYCMD=mysql -u$MYUSER -p$MYPASS -S $SOCKET[ -d "$DBPATH" ] || mkdir $DBPATHfor dbname in `$MYCMD -e "show databases;"|sed '1,2d'|egrep -v "mysql|schema"`do$MYDUMP $dbname|gzip >&DBANME/${dbname}_$(date + %F).sql.gzdone
例 10-8 实现 mysql 分表备份脚本
#!/bin/bashPATH="/application/mysql/bin:$PATH"DBPATH=/tmp/backupMYUSER=rootMYPASS=passwordSOCKET=/data/3306/mysql.sockMYCMD="msyql -u$MYUSER -p$MYPASS -S $SOCKET"MYDUMP="mysqldump -u$MYUSER -p$MYPASS -S $SOCKET"[ -d $DBPATH ] || mkdir $DBPATHfor dbname in `$MYCMD -e "show databases"|sed '1,2d'|egrep -v "mysql|schema"`dofor table in `$MYCMD -e "show tables from $dbname;"|sed '1d'`do$MYDUMP $dbname $table|gzip >$DBPATH/${dbname}_$(date +%F)/${dbname}_${table}.sql.gzdonedone
例 10-9 批量创建 5 个系统账号(ylt01-ylt05),并设置密码(密码为 8 位随机数,要求是字符和数字的混合)
#!/bin/bash. /etc/init.d/functionsuser="ylt"passfile="/tmp/user.log"for num in `seq -w 05`dopass="`echo "test$RANDOM"|md5sum|cut -c3-10`"useradd $user$num &>/dev/null &&\echo "$pass"|passwd -stdin $user$num &>/dev/null &&\echo -e "user:$user$num\tpasswd:$pass">>$passfileif [ $? -eq 0 ]; thenaction "$user$num is ok" /bin/trueelseaction "$user$num is fail" /bin/falsefidonecat $passfile && >$passfile
1)通过系统环境变量($RANDOM)实现
[root@web001 scripts]# echo $RANDOM12846
[root@web001 scripts]# echo ylt$RANDOM|md5sum|cut -c 1-506d50#ylt 就是上述加密字符串
2)通过 openssl 产生随机数
[root@web001 scripts]# openssl rand -base64 8s50Slkzo6VE=
3)通过时间(date)获得随机数
[root@web001 scripts]# date +%s%N1540551763039074396
4)通过 /dev/urandom 配合 chksum 生成随机数
[root@web001 scripts]# head /dev/urandom|cksum4002297225 3674
5)通过 UUID 生成随机数
[root@web001 scripts]# cat /proc/sys/kernel/random/uuid7f0f19cb-18dc-431e-b29e-a1c9e3ad9f38
6)使用 expect 附带的 mkpasswd 生成随机数
[root@web001 ~]# yum install -y expect[root@web001 ~]# mkpasswd -l 9 -d 2 -c 3 -C 3 -s 16SnadM<4J# -l (length of password, default = 9)# -d (min # of digits, default = 2)# -c (min # of lowewcase chars, default = 2)# -C (min # of uppercase chars, default = 2)# -s (min # of special chars, default = 1)
1)select 循环语句为变量取值型
select 变量名 [ in 菜单取值列表 ]docmd...done
例 10-10 用 select 循环打印菜单项的多种实现方法
1)直接使用列表字符串
[root@web001 scripts]# cat 242.sh#!/bin/bashselect name in ylt yyy lll tttdoecho $namedone[root@web001 scripts]# sh 242.sh1) ylt2) yyy3) lll4) ttt#? 1ylt#? 2yyy#? 3lll#? 4ttt#? ^C
2)采用数组做变量列表
[root@web001 scripts]# cat 242_1.sh#!/bin/basharray=(ylt yyy lll ttt)select name in "${array[@]}"doecho $namedone
3)把命令结果作为变量列表(菜单项)
[root@web001 scripts]# mkdir -p /tmp/test/{ylt,yyy,lll,ttt}[root@web001 scripts]# cat 242_2.sh#!/bin/bashselect name in `ls /tmp/test`doecho $namedone
例 10-11 调整 select 循环菜单项的默认提示符及利用 select 变量打印数字序号。
[root@web001 scripts]# cat 244.sh#!/bin/bashPS3="please select a num from menu:" # PS3 是系统环境变量用于控制 select 循环的提示符select name in ylt yyy lll tttdoecho -e "I guess you selected the menu is:\n $REPLY) $name"done[root@web001 scripts]# sh 244.sh1) ylt2) yyy3) lll4) tttplease select a num from menu:1I guess you selected the menu is:1) yltplease select a num from menu:^C