Linux shell编程 循环语句for while continue break exit

for循环是编程语言中一种循环语句

  for循环语法

#写法1 
for 变量 in 取值列表
do
    代码块
done

#写法2
for ((i==1;i<=100;i++))
do
    代码块
done

 while,until循环语法

while [表达式]
do
    条件满足执行的代码块
    变量的迭代方式
done



until [表达式]  #与while区别在于,while满足条件执行,until满足条件终止
do
    条件不成立执行的代码块
    变量的迭代方式
done

示例1:循环读取user.txt中的用户名,创建用户。设置密码。

for i in $(cat /opt/user.txt)
do
 useradd $i
 echo 123456 | passwd --stdin $i
done

示例2:循环读取ipaddr文本文件中地址,执行ping命令,获取结果。根据执行结果将存货的主机地址和不存活的主机地址区分写入两个文件

[root@xue opt]# cat pingtofile.sh
for i in $(cat /opt/ipaddr.txt)
do
ping -c 3 -W 2 $i &> /dev/null 
#-c 3 ping3次    -W 2 等待时间2s    &> /dev/null报错信息导入空设备不显示
if [ $? == 0 ]
then echo $i >> /opt/ipservive.txt
else echo $i >> /opt/ipdie.txt
fi
done

 

示例3         从1累加到100

sum=0
for i in {1..100}
do
  sum=$(($i+$sum))
done
echo $sum


常用转义字符

echo -n 表示不换行输出
echo -e 输出转义字符,将转义后的内容输出到屏幕上  

echo -ne 


只有加了-e才能执行下面的转义符:
\b 转义后相当于按退格键(backspace),但前提是"\b"后面存在字符;"\b"表示删除前一个字符,"\b\b"表示删除前两个字符。

\c 不换行输出,在"\c"后面不存在字符的情况下,作用相当于 echo -n; 但是当"\c"后面仍然存在字符时,"\c"后面的字符将不会被输出。

\n 换行,被输出的字符从"\n"处开始另起一行。 
\f 换行,但是换行后的新行的开头位置连接着上一行的行尾;

\v 与\f相同;

\t 转以后表示插入tab,即横向制表符;

\r 光标移至行首,但不换行,相当于使用"\r"以后的字符覆盖"\r"之前同等长度的字符;但是当"\r"后面不存在任何字符时,"\r"前面的字符不会被覆盖

\\ 表示插入"\"本身;

使用转义字符-n实现不换行效果

echo "-n不换行"
for i in {1..9}
do
  echo -n "*"
done

echo

echo "普通输出换行"
for i in {1..9}
do
  echo "*"
done

 

使用嵌套for循环搭配转义字符-n输出正三角

for i in {1..9} #外循环,实现行输出
do
  for ((j=1;j<=i;j++)) #内循环,实现列输出
  do
  echo -n "*"
  #每列不换行输出*,输出多少个*取决于上面的j循环(输出个数与行数相关)
  done
echo    #此echo为外循环每行换行使用
done

改进正三角,结合-ne 输出九九乘法表

for i in {1..9} #外循环,实现行输出
do
  for ((j=1;j<=i;j++)) #内循环,实现列输出
  do
  echo -ne "$i*$j=$(($i*$j))\t"
#-ne:n不换行输出,-e:为了使用转义符\t。\t:制表符 由于分隔输出
  done
echo    #此echo为外循环每行换行使用
done


跳出for循环:continue与break   

continue跳出循环,循环内部跳过本次循环并继续下一次循环

break打破循环,直接跳出循环不再执行

continue 2表示跳出2层循环

continue 3表示跳出3层循环

continue 4表示跳出4层循环

continue 5表示跳出5层循环

不写数字默认为1,continue 1跳出当前循环

break写法同理。

 

[root@xue opt]# cat continue.sh
#直接跳过1层当前循环
echo "continue"
for a in {1..5}
do
  for b in {1..5}
  do
    if [ $b -eq 3 ]
    then
    continue
    fi
  echo -ne "a=$a-b=$b\t\t"
  done
echo
done



echo
echo
echo
#直接跳过2层循环
echo "continue 2"
for a in {1..5}
do
  for b in {1..5}
  do
    if [ $b -eq 3 ]
    then
    continue 2
    fi
  echo -ne "a=$a-b=$b\t\t"
  done
echo
done



echo
echo
echo
#直接破除1层当前循环
echo "break"
for a in {1..5}
do
  for b in {1..5}
  do
    if [ $b -eq 3 ]
    then
    break
    fi
  echo -ne "a=$a-b=$b\t\t"
  done
echo
done



echo
echo
echo
#直接破除2层循环
echo "break 2"
for a in {1..5}
do
  for b in {1..5}
  do
    if [ $b -eq 3 ]
    then
    break 2
    fi
  echo -ne "a=$a-b=$b\t\t"
  done
echo
done

exit 退出当前脚本执行,自定义返回状态码

 由于脚本执行后使用预定义变量#?查看执行结果只能显示上一条命令执行是否发生了问题(例如此处的netstat)即使没有httpd服务也会正常执行返回0,此时可以使用exit 2,自定义返回2。

执行该脚本后在用#?查看,返回值为2。

(此处的事例仅仅作为一个演示,没有实际用途)




进阶例题

while 循环创建用户

i=1
while [ $i -le 10 ]
do
useradd user${i}
echo "123456" | passwd --stdin user${i} &> /dev/null
let i++
done

while 猜测价格

[root@xue opt]# cat caijia.sh
price=$[RANDOM%100+1]  #0-32767
i=0
while true
do
  read -p "input the price" exp
  let i++

  if [[ $exp -gt $price ]]
        then
        echo '高了!'

  elif  [[ $exp -lt $price ]]
        then
        echo '低了!'

  else
        echo '猜对了'
        break
  fi
done
echo "你猜了$i 次"

 

for 网段持续检测

read -p "请输入一个网段(such like 192.168.80)" wangduan
for zhuji in {1..254}
do
  ping -c 3 -W 2 ${wangduan}.${zhuji} &> /dev/null
  if [ $? -eq 0 ]
  then
    echo "${wangduan}.${zhuji} is online!!!"
    echo ${wangduan}.${zhuji} >> /opt/serviceip.txt
  else
    echo "${wangduan}.${zhuji} is offline"
  fi
done

 

 完善代码,添加  {  }& 并发。

由于ping需要时间,一个个ping耗时太长,使用  {  }&  包裹ping语句,使其并发执行

read -p "请输入一个网段(such like 192.168.80)" wangduan
for zhuji in {1..254}
do
{               #✨
  ping -c 3 -W 2 ${wangduan}.${zhuji} &> /dev/null
  if [ $? -eq 0 ]
  then
    echo "${wangduan}.${zhuji} is online!!!"
    echo ${wangduan}.${zhuji} >> /opt/serviceip.txt
  else
    echo "${wangduan}.${zhuji} is offline"
  fi
  }&            #✨
done
wait   #✨若有的线程较快,会直接执行下面的cat导致显示不全,加上wait,使得所有线程执行完后才执行下面的命令

cat /opt/serviceip.txt

for 多文件合并到一个文件

for sb in /opt/*.sh      #for循环查找文件
do
  cat "$sb" >> hebing.txt     #内容重定向到文本文件
done

for 显示文件夹所有文件 (在生产环境中不允许使用ll,ls命令。可以通过shell脚本获取)

for sb in *
 do
 echo "$sb"
 done

 改进,排除文件夹

for sb in *
do
 test -f $sb  #是否为文件 (排除目录)
 if [ $? -wq 0 ]
    then
    echo "$sb"
 fi
done
~

while shell计算器

while true   ==   for ((;;))
#都可以死循环
while true
do

read -p '输入数字1   ' num1
read -p '选择加减乘除+—x/   ' jjcc
read -p '输入数字2   ' num2
if [ $jjcc == '+' ]
 then
 echo $(($num1+$num2))
fi
if [ $jjcc == '-' ]
 then
 echo $(($num1-$num2))
fi
if [ $jjcc == 'x' ]
 then
 echo $(($num1*$num2))
fi
if [ $jjcc == '/' ]
 then
 echo $(($num1/$num2))
fi
echo

done

优化版代码 

使用[[   ]]

变量全部加上"  "

符合语言规范

while true
do
  read -p "请输入第一个整数:" num1
  read -p "请输入运算符:加(+);减(-);乘(*);除(/);求余(%):" fh
  read -p "请输入第二个整数:" num2
  if [[ "$fh" == "+" ]]
  then
    echo "结果为:$(($num1 + $num2))"
  elif [[ "$fh" == "-" ]]
  then
    echo "结果为:$(($num1 - $num2))"
  elif [[ "$fh" == "*" ]]
  then
    echo "结果为:$(($num1 * $num2))"
  elif [[ "$fh" == "/" ]]
  then
    echo "结果为:$(($num1 / $num2))"
  elif [[ "$fh" == "%" ]]
  then
    echo "结果为:$(($num1 % $num2))"
  else
    echo "输入有误!"
  fi
done

 

while  商店选购

选择是否进入商店。进入商店则选购产品。不进入商店则结算。显示花费了多少资金。

[root@xue opt]# cat shop.sh
sum=0
count=0
while true
  do
   read -p "是否进入商店?y/n   " enter
   if [ $enter == "y" ]
   then
         let count++
         read -p "输入商品数字 1.衣服500 2.裤子400 3.鞋子350 4.帽子150 5.袜子50   " sp
         case $sp in
         1)
         let sum+=500
         ;;
         2)
         let sum+=400
         ;;
         3)
         let sum+=350
         ;;
         4)
         let sum+=150
         ;;
         5)
         let sum+=50
         ;;
         *)
         break
         esac
   else break
   fi
   done
echo "共进入商店$count 次 ,共消费$sum 元"

小技巧 seq命令

seq 1 2 10    #从1开始,每隔2,输出直到10
seq 2 3 10    #从2开始,每隔3,输出直到10

  • 0
    点赞
  • 3
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值