1for循环结构语法及实例

1.1for循环结构语法1

for 变量名 in 变量取值列表

do

    指令……….

done

提示:此结构中“in 变量取值列表”可省略,省略时相当于in “$@”,使用for i就相当于使用for i in “$@”

1.2for循环结构语法2

for ((exp1;exp2;exp3)); do

        指令…………

   done

image.png

exp1只执行一次,相当于在for里嵌了while

1.3for循环结构基础实例

1for循环直接输出元素51的方法

#!/bin/bash

for num in 5 4 3 2 1

  do

   echo $num

 done

2for循环使用大括号的方法输出元素51

#!/bin/bash

for num in {5..1}

  do

   echo $num

 done

 

3for循环使用seq方法实现输出元素51

#!/bin/bash

for num in `seq -s " " 5 -1 1` 

#这里-s指定分隔符为空格,5为第一个输出字符,-1为步长,1为最后一个字符

  do

   echo $num

 done

 

4:使用for循环进行文件批量改名,把jpg改成gif

[root@localhost test]# ls

1.jpg  2.jpg  3.jpg  4.jpg  5.jpg

[root@localhost test]# for a in `ls /root/test/`;do mv $a `echo $a|cut -d . -f1`.gif; done

[root@localhost test]# ls

1.gif  2.gif  3.gif  4.gif  5.gif

 

5for循环在/abc目录下创建文件abc-1abc-10

#!/bin/bash

mkdir /abc && cd /abc

for a in {1..10}

   do

  touch abc-$a

done

 

6for循环批量创建10个普通用户abc-01abc-10,密码设置为aaa-01aaa-10

#!/bin/bash

for num in `seq -w 10`   #说明:-w0补充列宽

  do

   useradd abc-$num

   echo "aaa-$num"|passwd --stdin "abc-$num"

 done

 

7for循环批量创建用户密码为8位随机字符串

#先实现8位随机数的取值

[root@localhost ~]# echo $(date +%N)   #%N微秒,每次数字很难相同

099765771

[root@localhost ~]# echo $RANDOM   #随机函数,每次值都不同

11755

[root@localhost ~]# echo $(date +%N)$RANDOM   #两个组合生成更加不同的随机数

73312156513717

[root@localhost ~]# echo $(date +%N)$RANDOM|md5sum|cut -c 1-8  

#把随机数再使用md5加密,然后取8位即可

e65d36e5

 

#脚本创建用户随机密码实现:

#!/bin/bash

for num in `seq -w 10`

  do

#注意:这里一定要定义密码的变量,不然后面echo输出的密码就不正确了。

   password=$(echo $(date +%N)$RANDOM|md5sum|cut -c 1-8)

   useradd abc-$num

   echo "aaa-$num"|passwd --stdin "abc-$num"

   echo -e "用户名:abc-$num 密码:$password" >>/root/user.txt

 done

 

一句话实现方式:

[root@localhost ~]# for num in `seq -w 10`;do  password=$(echo $(date +%N)$RANDOM|md5sum|cut –c 1-8);echo -e "用户名:abc-$num 密码:$password";done

用户名:abc-01 密码:66e7c7ab

用户名:abc-02 密码:34dd9e01

用户名:abc-03 密码:9accf4e5

用户名:abc-04 密码:919cad0a

用户名:abc-05 密码:b2c259c0

用户名:abc-06 密码:c59e255f

用户名:abc-07 密码:bd8bd4f7

用户名:abc-08 密码:62b9633d

用户名:abc-09 密码:cac00924

用户名:abc-10 密码:839317aa

 

8:求出(1+2+3...+n)的总和

#!/bin/bash

sum=0

read -p "请输入一个需要从1加到多少的整数:" num

if [[ $num =~ [^0-9] ]];then

   echo "输入有误,请输入大于0的整数!!!"

elif [[ $num -eq 0 ]];then

   echo "输入有误,请输入大于0的整数!!!"

else

   for i in $(seq 1 $num);do

      sum=$[$sum+$i]

   done

   echo $sum

fi

分析:sum初始值为0,请输入一个数,先判断输入的是否含有除数字以外的字符,有就报错;没有判断是否为0,不为0进入for循环,i的范围为1~输入的数,每次的循环为sum=sum+i,循环结束,最后输出sum的值。

 

9:计算1+3+5+.....+100所有奇数的和

#!/bin/bash

for ((i=1,sum=0;i<=100;i++));do

  [ $[i%2] -eq 1 ] && let sum+=i

done

echo sum=$sum

1.4for循环中循环体可并行执行,使脚本运行更快

用法:给for循环的循环体加上大括号,然后在大括号后面加上&符号即可

for name in 列表 ;do

  {

  循环体

  }&

done

wait

1.5for循环并行检测局域网中存活的主机

搜寻自己指定ip(子网掩码为24的)的网段中,UPip地址

#!/bin/bash

#说明:此脚本是用来检测局域网中指定的网段有哪些主机开启

#用法:直接执行此脚本,然后输入你想探测的网段地址即可,例如:192.168.10.0网段有哪些主机开启

read -p "请输入你想查看主机为开启状态的网段地址[例如:192.168.1.0]" net

echo $net | egrep -o "\<(([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])\.){3}([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|[25[0-5]])\>"

[ $? -eq 0 ] || (echo "你的输入有误,请重新输入!!!";exit 10)

IP=$(echo $net|egrep -o "^([0-9]{1,3}\.){3}")

   for i in {1..254};do

      {

#       echo $IP$i

       ping -c 1 -w 1 $IP$i &> /dev/null && echo "$IP$i 主机开启"

      }&

done

分析:请输入一个IP地址例192.168.37.234,如果格式不是0.0.0.0 则报错退出;正确则进入循环,IP变量的值为192.168.37.  i的范围为1-254,并行ping 192.168.37.1-154ping通就输出此IPUP。直到循环结束。

经过测试:上面这个脚本如果循环体大括号后面不加&符号,运行完需要200多秒,加上&之后,运行2秒即可完成。

 

 

2while循环结构语法及实例

2.1while循环结构语法

while循环控制条件

 do

     指令

   done

循环控制条件;进入循环之前,先做一次判断;每一次循环之后会再次做判断;条件为“true ,则执行一次循环;直到条件测试状态为“false 终止循环

2.2、特殊用法(遍历文件的每一行)

while read line; do

  循环体

done < /PATH/FROM/SOMEFILE

 

cat /PATH/FROM/SOMEFILE | while read line; do

  循环体

done

依次读取/PATH/FROM/SOMEFILE文件中的每一行,且将行赋值给变量line

2.3100以内所有正奇数之和

#!/bin/bash

sum=0

i=1

while [ $i -le 100 ];do

   if [ $[$i%2] -ne 0 ];then

      let sum+=i

      let i++

   else

      let i++

   fi

done

echo "100以内所有奇数之和为:$sum"

分析:sum初始值为0i的初始值为1;请输入一个数,先判断输入的是否含有除数字以外的字符,有,就报错;没有当i<100时,进入循环,判断 i÷2取余 是否不为0,不为0时奇数,sum=sum+ii+1,为0i+1;循环结束,最后输出sum的值。

2.4、每隔2秒记录一次系统负载情况

#!/bin/bash

while true

  do

    uptime

    sleep 2

  done

提示:while true表示条件永远为真,会一直运行,这种我们称为守护进程。

 

2.5、把执行内容追加到log里,使用微秒为单位

#!/bin/bash

while [ 1 ]

  do

    uptime >>./uptime.log

    usleep 1000000    #这里是微秒单位,1秒等于1000000微秒

  done

2.6、使用while循环计算从1加到1000000

#!/bin/bash

i=1

sum=0

while((i<=1000000))

do

  ((sum=sum+i))

  ((i++))

done

echo "sum=$sum"

以上脚本执行的时间

[root@localhost ~]# time bash 1.sh

sum=500000500000

real       0m15.501s

user      0m14.611s

sys       0m0.737s

 

2.7、使用计算公式计算从1加到1000000

#!/bin/bash

#快速求和计算公式((sum=n*(n+1)/2))

n=1000000

((sum=$n*($n+1)/2))

echo "sum=$sum"

以上脚本执行的时间

sum=500000500000

real         0m0.024s

user         0m0.006s

sys          0m0.015s

可以看到使用算法公式的效率要比没有使用算法公式的while快很多倍。

2.8while读入文件内容的3种方式

方法1

exec < FILE

sum=0

while read line

  do

     cmd

done

 

方法2

cat ${FILE_PATH} | while read line

  do

    cmd

  done

 

方法3

while read line

  do

    cmd

  done < FILE

 

3until循环结构语法及实例

3.1until循环结构语法

until 循环条件

   do

     指令

   done

until是条件不满足就一直执行下面的指令,条件满足就会退出

提示:until应用场合不多,了解就行

3.2、监控user1用户,发现登录就杀死

#!/bin/bash

until pgrep -u user1 &> /dev/null;do

   sleep 1

done

pkill -9 -u user1

分析:每隔1秒扫描,直到发现user1用户登录,杀死这个进程,退出脚本,用于监控用户登录

3.3until1加到100范例

#!/bin/bash

i=1

until ((i>100))

  do

   ((sum=sum+i))

   ((i++))

done

echo $sum

可以看出until是不满足条件就执行循环,满足条件就退出         

4select 循环结构语法及实例

4.1select循环结构语法

select variable in list

do

  循环体命令

done

 

1select 循环主要用于创建菜单,按数字顺序排列的菜单项将显示在标准错误上,并显示PS3 提示符,等待用户输入

2、用户输入菜单列表中的某个数字,执行相应的命令

3、用户输入被保存在内置变量 REPLY

4select 是个无限循环,因此要记住用 break 命令退出循环,或用 exit 命令终止脚本。也可以按 ctrl+c退出循环

5select 经常和 case 联合使用

6、与for循环类似,可以省略 in list 此时使用位置参量

4.2select循环结构实例

#!/bin/bash

PS3="请输入你需要选择的菜单序号:"

select menu in 米饭 包子 饺子 面条 quit;do

   case $REPLY in

   1|2)

      echo "你选择的是米饭或包子,价格为3元每份。"

;;

   3|4)

      echo "你选择的是饺子或面条,价格为10元每份。"

;;

   5)

      break

;;

   *)

      echo "没有这个选项,请重新选择!!!"

   esac

done

运行结果:

[root@localhost script]# bash select.sh

1) 米饭

2) 包子

3) 饺子

4) 面条

5) quit

请输入你需要选择的菜单序号:2

你选择的是米饭或包子,价格为3元每份。

请输入你需要选择的菜单序号:3

你选择的是饺子或面条,价格为10元每份。

请输入你需要选择的菜单序号:6

没有这个选项,请重新选择!!!

请输入你需要选择的菜单序号:5

[root@localhost script]#

 

到此,shell中的四大循环结构就介绍完毕了。