20160909 补充break与continue的区别程序员
什么是循环语句、死循环?docker
循环语句:将一段代码重复执行0、1或屡次。编程
到底要重复运行多少次?以及咱们如何设定循环语句的重复次数?bash
为了解决上面的问题因而就有了进入条件与退出条件。ide
进入条件:条件知足时进入循环。工具
退出条件:不符合条件退出循环。性能
一种特殊的循环:死循环测试
死循环:在编程中,一个没法靠自身的控制终止的循环称为"死循环"。死循环的出现有两种状况:ui
一、因程序须要刻意写的;二、因程序员的失误形成的。spa
第二种的死循环一般会形成比较严重的程序错误,甚至会所以而影响物理机。所以死循环的使用须要合理的设计。
实验环境CentOS7.2
本文重要的三个循环语句:for、while、until
………………………………………………………………………………………………………………………
for循环
for语句的使用格式:
for NAME in LIST(列表); do
循环体
done
列表生成方式:
(1) 整数列表
{start..end}
$(seq start [[step]end])
(2) glob
/etc/rc.d/rc3.d/K*
(3) 命令
………………………………………………………………………………………………………………………
下面以一个例子看看for的具体做用
示例:计算1+2+...+10的值
#!/bin/bash #sum the value of "1+2+...+10" #author chawan #date:20160906 declare -i sum=0 for x in {1..10};do let sum+=$x done echo "The sum is : $sum"
运行脚本0906-1结果以下
[root@docker hmworks]# sh 0906-1 The sum is : 55
上面使用了第一种的整数列表中的第一种形式,这里若是是“1+2+...+n”这种形式那么{start..end}就再也不适用,此时就只能使用$(seq start [[step]end])。下面再举一个例子说明
示例:计算“1+2+...+n”的值
#!/bin/bash #sum “1+2+...+n” #author chawan #date:20160906 declare -i sum=0 #以交互的方式输入一个正整数 read -p "Please inset a number :" num #判断输入的数是否为空,为空则提示并退出 [ -z $num ] && echo "Please input a number!" && exit 1 #判断输入的是不是正整数,如果则执行循环,若不是提示输入正整数并退出 if [[ $num =~ ^[1-9][0-9]{0,}$ ]] ; then for i in {1..$num};do #for i in `seq 1 $num`;do let sum+=$i #sum=$[$sum+$i] 这种方式也能够不过不够简练 done else echo "Error : please input a positive integer" && exit 2 fi #显示最后的和 echo "The sum is : $sum"
下面执行该脚本
[root@docker hmworks]# sh 0906-2 Please inset a number :8 0906-2:行14: let: sum+={1..8}: 语法错误: 期待操做数 (错误符号是 "{1..8}") The sum is : 0
该结果说明{start..end}形式不适用于有变量出现的状况,既然这个不行就来试试$(seq start [[step]end])
#!/bin/bash #sum “1+2+...+n” #author chawan #date:20160906 declare -i sum=0 #以交互的方式输入一个正整数 read -p "Please inset a number :" num #判断输入的数是否为空,为空则提示并退出 [ -z $num ] && echo "Please input a number!" && exit 1 #判断输入的是不是正整数,如果则执行循环,若不是提示输入正整数并退出 if [[ $num =~ ^[1-9][0-9]{0,}$ ]] ; then for i in `seq 1 $num`;do let sum+=$i #sum=$[$sum+$i] done else echo "Error : please input a positive integer" && exit 2 fi #显示最后的和 echo "The sum is : $sum"
执行该脚本
[root@docker hmworks]# sh 0906-2 Please inset a number :10 The sum is : 55 [root@docker hmworks]# sh 0906-2 Please inset a number :100 The sum is : 5050
该结果代表$(seq start [[step]end])适用性更好,所以通常建议使用它。
列表的glob与命令这两种就再也不具体演示。你们感兴趣能够本身尝试下作个实验体会体会。
………………………………………………………………………………………………………………………
while循环
while语句使用格式:
while CONDITION; do
循环体
done
CONDITION:循环控制条件;进入循环以前,先作一次判断;每一次循环以后会再次作判断;条件为“true”,则执行一次循环;直到条件测试状态为“false”终止循环;
所以:CONDTION通常应该有循环控制变量;而此变量的值会在循环体不断地被修正;
进入条件:CONDITION为true;
退出条件:CONDITION为false
………………………………………………………………………………………………………………………
示例:计算1+2+...+10的值
#!/bin/bash #sum the value of "1+2+...+10" while #author chawan #date:20160906 #为了严谨起见,事先声明变量sum及i为整数型 declare -i sum=0 declare -i i=1 while [ $i -le 10 ];do let sum+=$i #sum=$[$sum+$i]的简写形式 let i++ #不断修正变量体 done echo "The sum is : $sum"
执行脚本,查看其是否正确执行
[root@docker hmworks]# sh 0906-3 The sum is : 55
while与for的不一样在于:
一、不须要列表,所以能够大大节省内存空间,由于for若是列表很大会占用较多内容空间,对系统性能会形成影响,因此此时while的优越性就显现出来,它不须要占用不少内存空间,只须要两个变量的空间及作加法便可。
二、while须要修正体来不断修正变量,最终在符合退出条件时结束循环。
………………………………………………………………………………………………………………………
until循环
until语句使用格式:
until CONDITION; do
循环体
done
CONDITION:循环控制条件;进入循环以前,先作一次判断;每一次循环以后会再次作判断;条件为“false”,则执行一次循环;直到条件测试状态为“true”终止循环;
所以:CONDTION通常应该有循环控制变量;而此变量的值会在循环体不断地被修正;
进入条件:CONDITION为false;
退出条件:CONDITION为true
until的用法同while,惟一的区别在于进入循环与退出循环的条件相反。
以相同的例子来体会两者的区别
………………………………………………………………………………………………………………………
示例:计算1+2+...+10的值
#!/bin/bash #sum the value of "1+2+...+10" until #author chawan #date:20160906 declare -i sum=0 declare -i i=1 until [ $i -gt 10 ];do let sum+=$i let i++ done echo "The sum is : $sum"
执行脚本,查看结果是否正确输出
[root@docker hmworks]# sh 0906-4 The sum is : 55
经过比较while与until的惟一差异就在于判断条件。这二者其实算是同一种循环语句,只是进入及退出循环的条件正好相反。
循环控制语句(用于循环体中)
一、continue [N]:提早结束第N层的本轮循环,而直接进入下一轮判断;
其使用格式:
while CONDTIITON1; do
CMD1
...
if CONDITION2; then
continue
fi
CMDn
...
done
………………………………………………………………………………………………………………………
示例:求100之内全部偶数之和;要求循环遍历100之内的所正整数
#!/bin/bash #求100之内全部偶数之和;要求循环遍历100之内的所正整数 #author chawan #date:20160906 declare -i i=1 declare -i sum=0 while [ $i -le 100 ];do let i++ #若是为奇数则跳过该循环 if [ $[${i}%2] -eq 1 ];then continue fi let sum+=$i done echo "The even number sum : $sum"
执行脚本,查看结果是否正确显示
[root@docker hmworks]# sh 0906-5 The even number sum : 2550
以前我写这个脚本时是这么写的
#!/bin/bash #求100之内全部偶数之和;要求循环遍历100之内的所正整数 #author chawan #date:20160906 declare -i i=1 declare -i sum=0 while [ $i -le 100 ];do let sum+=$i #若是为奇数则跳过该循环,直接进入下一轮判断后面的程序再也不执行 if [ $[${i}%2] -eq 1 ];then continue fi let i++ done echo "The even number sum : $sum"
这就是我我的因为对continue的理解不够准确而形成的死循环。
因为continue是跳过其所在循环,直接进入下一轮判断,后面的语句都再也不执行。
当时没注意这点因此错误地把i++放在后面,这就致使若i起始值为奇数那么它就一直在重复执行。
这里只要将let sum+=$i与let i++调换为止便可正确执行。
………………………………………………………………………………………………………………………
二、break [N]:提早结束循环;
其使用格式:
while CONDTIITON1; do
CMD1
...
if CONDITION2; then
break
fi
CMDn
...
done
break的使用一般是与死循环同时出现的,下面来介绍如何建立死循环
建立死循环:
while true; do
循环体
done
until false; do
循环体
done
………………………………………………………………………………………………………………………
示例:每隔3秒钟到系统上获取已经登陆的用户的信息;若是docker登陆了,则记录于日志中,并退出;
#!/bin/bash #每隔3秒钟到系统上获取已经登陆的用户的信息;若是docker用户登陆,则记录于日志中,并退出脚本 #author chawan #date:20160906 while true;do if who | grep "^docker\>" $> /dev/null;then break fi sleep 3 echo "docker is not login" done echo "docker logged on." >> /tmp/user.log
运行脚本
[root@docker hmworks]# sh 0906-6 docker is not login docker is not login docker is not login docker is not login docker is not login docker is not login
为了验证该脚本,下面咱们使用docker用户登录
docker用户登录后查看/tmp/user.log文件
#########################################################################################
break与continue语句的区别:
break语句和continue语句均可以位于各类循环体内,用于控制当前的循环流程。但,break语句是直接退出当前的循环结构,转向执行循环体后面的语句;而continue语句则只是跳过当前循环体中continue语句后面的语句,转向当前循环体的起始位置,从新执行下一次循环,并无退出当前的循环结构。
这是二者最本质的区别:break跳出当前循环,continue没有跳出当前循环。
循环语句的特殊用法(while及for)
while循环的特殊用法(遍历文件的每一行):
其使用格式:
while read line; do
循环体
done < /PATH/FROM/SOMEFILE
依次读取/PATH/FROM/SOMEFILE文件中的每一行,且将行赋值给变量line
………………………………………………………………………………………………………………………
示例:找出其ID号为偶数的全部用户,显示其用户名及ID号;
#!/bin/bash #找出其ID号为偶数的全部用户,显示其用户名及ID号 #author chawan #date:20160906 while read line;do if [ $[`echo $line | cut -d: -f3`%2] -eq 0 ];then echo -e -n "username: `echo $line|cut -d: -f1`\t" echo "uid:`echo $line|cut -d: -f3`" fi done < /etc/passwd
运行脚本
………………………………………………………………………………………………………………………
for循环的特殊格式:
for ((控制变量初始化;条件判断表达式;控制变量的修正表达式)); do
循环体
done
控制变量初始化:仅在运行到循环代码段时执行一次;
条件判断表达式:在什么条件下进行循环;
控制变量的修正表达式:每轮循环结束会先进行控制变量修正运算,然后再作条件判断;
示例:求100之内所正整数之和
#!/bin/bash #求100之内所正整数之和 #author chawan #date:20160906 declare -i sum=0 for ((i=1;i<=100;i++));do let sum+=$i done echo "The sum is : $sum"
运行脚本,查看结果是否正确
[root@docker hmworks]# sh 0906-8 The sum is : 5050
for的这种格式减小了代码量,看着更简洁,不过其限制是只适用于有数字出现的循环,如果对某目录下的全部文件进行某种循环的执行就不适应了。
循环嵌套
在本文的最后再以一题体会下循环嵌套的神奇
示例:打印九九乘法表
#!/bin/bash #打印九九乘法表 #author chawan #date : 20160906 for((j=1;j<=9;j++));do for((i=1;i<=j;i++))do echo -e -n "${i}X${j}=$[$i*$j]\t" done echo done
我在刚刚接触循环嵌套时各类晕,循环嵌套不是没有目的的乱用,而是根据本身的需求有目的的使用,好比要打印99乘法表,开始要分析99乘法表的规律,分析后咱们发现它横行是连续的,所以要用到一个循环(一般在遇到连续的内容都会用到循环)它的列也是连续的,所以又用到一个循环,而99乘法表又是由两个变化的量构成,综上咱们就能够肯定,须要使用两个变量,这两个变量分别要用到循环,而一个变量又受到另外一个变量的限制,所以这个受限的变量就是被嵌套的主。问题分析到这里,咱们解决这个问题要用到的工具都找出来了:两个变量,每一个变量对应一个循环,同时一个变量受到另外一个变量的限制,也就是说它须要在其循环内进行嵌套。
下面就是靠本身去使用工具解决问题了。我相信你们这点应该都不成问题,问题就分析到这里。
小结:
本文主要介绍什么是循环,死循环,bash经常使用的三种循环语句for、while、until及循环控制语句continue、break
在本文结尾又介绍了while的特殊用法(遍历文件中的每一行),for的c语言格式。
至于何时用for何时用while须要本身在实际写脚本中细细比较,鉴于本人也是新手,这里就算想细说也只能望洋兴叹。