• 欢迎访问显哥博客,本网站纯属学习技术,绝无商业用途,欢迎小伙伴们共同学习!研究技术!QQ:52249909 加我QQ
  • 世界75亿人,这么小的概率,能认识你,是我一生的幸运,不妨加个QQ接触一下:52249909 加我QQ

Shell脚本编程学习——循环语句之For循环【显哥出品,必为精品】

Shell编程 lixian 4年前 (2020-04-26) 1294次浏览 1个评论 扫描二维码
文章目录[隐藏]

一、For循环基本概述

Shell脚本编程学习——循环语句之For循环【显哥出品,必为精品】

1.语法格式

for  变量名   in    取值列表
do
	循环体
done

当条件为真时,执行循环体,当条件为假时,循环体结束

2.for循环基本使用示例

[root@xian /server/scripts]# cat for-1.sh 
#!/bin/bash
# File Name: for-1.sh
# Author: lixian
#######################
for i in 1 2 3
do
    echo "$i"
done
[root@xian /server/scripts]# sh for-1.sh 
1
2
3

3.取值列表

默认取值 in后面的就是取值的内容 默认是以空白字符为分割符 空格 tab键 回车键都属于空白字符

取值列表中出现特殊字符,需要进行转义

4.自定义Shell分隔符

默认情况以空格为分隔符。通过IFS来自定义分隔符

#以冒号做分隔符 IFS=:

#以冒号,分号和双引号作为字段分隔符 IFS=:;”

#以换行符作为字段分隔符 IFS=$’\n’

以回车为分隔符示例

[root@xian /server/scripts]# cat for-1.sh 
#!/bin/bash
# File Name: for-1.sh
# Author: lixian
#######################
IFS=$'\n'
for i in `cat /etc/hosts`
do
    echo "$i"
done
[root@xian /server/scripts]# sh for-1.sh 
127.0.0.1   localhost localhost.localdomain localhost4 localhost4.localdomain4
::1         localhost localhost.localdomain localhost6 localhost6.localdomain6

定义多个分隔符(以冒号和空格为分隔符)示例

[root@xian /server/scripts]# cat test.txt 
root:x:0:0 root:/root /bin/bash
[root@xian /server/scripts]# sh for-1.sh 
root
x
0
0
root
/root
/bin/bash

二、 For循环C语言风格

1.语法格式

for        ((i=0;i<10;i++))
do
    commands
done

2.c语言风格for循环示例

[root@xian /server/scripts]# cat c_for.sh 
#!/bin/bash
# File Name: c_for.sh
# Author: lixian
#######################
for ((i=0,j=9;i<10;i++,j--))
do
    echo "$i + $j = $(($i+$j))"
done
[root@xian /server/scripts]# sh c_for.sh 
0 + 9 = 9
1 + 8 = 9
2 + 7 = 9
3 + 6 = 9
4 + 5 = 9
5 + 4 = 9
6 + 3 = 9
7 + 2 = 9
8 + 1 = 9
9 + 0 = 9

3.shell风格for循环示例

[root@xian /server/scripts]# cat for_for.sh 
#!/bin/bash
# File Name: for_for.sh
# Author: lixian
#######################
a=0
b=9
for i in {1..10}
do
    echo "$a + $b = $(($a+$b))"
    let a++
    let b--
done
[root@xian /server/scripts]# sh for_for.sh 
0 + 9 = 9
1 + 8 = 9
2 + 7 = 9
3 + 6 = 9
4 + 5 = 9
5 + 4 = 9
6 + 3 = 9
7 + 2 = 9
8 + 1 = 9
9 + 0 = 9

三、通过读入文件的方式进行创建用户

1.需要创建用户的文件列表

[root@xian /server/scripts]# cat useradd.txt 
lx1
lx2
lx3
lx4
lx5

2.脚本代码

[root@xian /server/scripts]# cat for_useradd_lixian.txt.sh 
#!/bin/bash
# File Name: for_useradd.sh
# Author: lixian
#######################
[ -f /etc/init.d/functions ] && source /etc/init.d/functions
for i in $(cat useradd.txt)
do
    id ${i%%:*} &>/dev/null
    if [ $? -eq 0 ];then
        action "${i%%:*}已经存在!不能重复创建!" /bin/false
    else
    useradd ${i%%:*} &>/dev/null && echo ${i#*:} | passwd --stdin ${i%%:*} &>/dev/null
    if [ $? -eq 0 ];then
        action "用户${i%%:*}创建成功!" /bin/true
    else
        action "用户${i%%:*}创建失败!" /bin/false
    fi
    fi
done

3.执行结果

[root@xian /server/scripts]# sh for_useradd_lixian.txt.sh 
用户lx1创建成功!                                          [  成功  ]
用户lx2创建成功!                                          [  成功  ]
用户lx3创建成功!                                          [  成功  ]
用户lx4创建成功!                                          [  成功  ]
用户lx5创建成功!                                          [  成功  ]
[root@xian /server/scripts]# sh for_useradd_lixian.txt.sh 
lx1已经存在!不能重复创建!                                [失败]
lx2已经存在!不能重复创建!                                [失败]
lx3已经存在!不能重复创建!                                [失败]
lx4已经存在!不能重复创建!                                [失败]
lx5已经存在!不能重复创建!                                [失败]

四、批量创建用户脚本

1.脚本代码

[root@xian /server/scripts]# cat useradd.sh 
#!/bin/bash
# File Name: useradd.sh
# Author: lixian
#######################
#调用函数
[ -f /etc/init.d/functions ] && source /etc/init.d/functions 
#提示用户输入创建用户的前缀
read -p "请输入你要创建用户的前缀(必须为字母):" Qz
#判断用户输入的前缀是否为字母
if [[ ! $Qz =~ ^[a-Z]+$ ]];then
    action "错误:您输入的内容不符合要求!" /bin/false
    exit
fi
#提示用户输入创建用户的数量
read -p "请输入创建用户的数量:" Num
#判断用户输入的数量是否为数字
if [[ ! $Num =~ [0-9]+$ ]];then
    action "错误:您输入的数字不符合要求" /bin/false
    exit
fi
#提示用户需要创建用户列表
echo "你创建用户为:${Qz}1..${Qz}${Num}"
read -p "你是否要创建这些用户?[yes/no]:" Confirm
#判断用户输入的选择
case $Confirm in
    Yes|yes|Y|y)
        action "收到指令!即将为您创建用户!" /bin/true
        for i in $(seq $Num)
        do
            User=${Qz}${i}
            id $User &>/dev/null
            if [ $? -eq 0 ];then
                action "用户${User}已经存在!" /bin/false
            else
                useradd $User &>/dev/null
                if [ $? -eq 0 ];then
                    action "${User}用户创建成功!" /bin/true
                else
                    action "${User}用户创建失败!" /bin/false
                fi
            fi
        done
        ;;
    No|no|N|n)
        action "收到指令!拒绝创建用户!" /bin/true
        exit
        ;;
    *)
        action "错误:您输入的内容不符合要求!" /bin/false
        exit
esac

2.执行结果

Shell脚本编程学习——循环语句之For循环【显哥出品,必为精品】

五、系统管理工具箱脚本

1.脚本代码

[root@xian /server/scripts]# cat menu_case.sh 
#!/bin/bash
# File Name: case-1.sh
# Author: lixian
#######################
#1.定义菜单函数
[ -f /etc/init.d/functions ] && source /etc/init.d/functions
menu() {
cat<<EOF
+---------------------------+
|                           |
|    1. 帮助信息            |
|    2. 系统版本信息        |
|    3. 系统内核信息        |
|    4. 磁盘使用情况        |
|    5. 内存使用情况        |
|    6. 系统负载情况        |
|    7. 用户登录情况        |
|    8. 所有IP地址          |
|    9. 外网IP地址          |
|    0. 退出脚本            |
|                           |
+---------------------------+
EOF
}
menu
while true
do
#提示用户进行输入想要查看的信息

    read -p "请根据菜单输入对应的数字获取对应的状态信息:" Num
#编写数字对应的功能命令

    case $Num in
        1)
            clear
            menu
            ;;
        2)
            echo "当前系统版本信息如下:"
            awk '{print $1,$4}' /etc/redhat-release
            ;;
        3)
            echo "当前系统内核版本信息如下:"
            uname -r
            ;;
        4)
            echo "当前系统磁盘使用情况如下:"
            df -h
            ;;
        5)
            echo "当前系统内存使用情况如下:"
            free -m
            ;;
        6)
            echo "当前系统负载情况如下:"
            uptime
            ;;
        7)
            echo "当前系统用户登录的情况如下:"
            w
            ;;
        8)
            echo "当前系统Eth0网卡IP地址如下:"
            ifconfig eth0 | awk 'NR==2{print $2}'
            ;;
        9)
            echo "当前系统外网IP地址如下:"
            curl -s ifconfig.me
            echo
            ;;
        0)
            action "你已经成功退出了脚本!" /bin/true
            exit
    esac
done

2.执行结果

Shell脚本编程学习——循环语句之For循环【显哥出品,必为精品】

六、实现简单的Jumpserver

1.业务需求

1. 执行脚本时,可以看到你所能够管理的主机 主机清单

2. 提示用户要进行管理哪台主机 连接某台主机

3. 需要写个循环,连接完一台主机后,还可以继续连接其他主机 不能退出脚本

4. 不能让跳板机可以使用Ctrl + c d z 等操作

5. 用户不能管理你的跳板机 每次登陆系统,自动执行脚本

6. 给自己留个后门,自己能够出去,退出脚本,不能告诉别人怎样退出脚本

2.脚本代码

[root@xian /server/scripts]# cat jumpserver.sh 
#!/bin/bash
# File Name: jumpserver.sh
# Author: lixian
#######################
#调用函数
[ -f /etc/init.d/functions ] && source /etc/init.d/functions
Menu(){
cat<<EOF
+-----------------------------+
|                             |
|      Jumpserver跳板机       |
|                             |
|   0.显示主机清单            |
|   1.连接-lb01 -172.16.1.5   |
|   2.连接-web01-172.16.1.7   |
|   3.连接-db01 -172.16.1.51  |
|   4.退出jumpserver脚本      |
|                             |
+-----------------------------+
EOF
}
#打印主机列表
Menu
#禁止执行Ctrl+c Ctrl+d Ctrl+z 等操作
trap "" HUP INT TSTP
#进行循环操作
while true
do
    #提示用户输入需要连接哪台主机
    read -p "请输入你需要操作的序号:" Num
    #判断用户输入的是否为数字
    if [[ ! $Num =~ ^[0-4]$ ]];then
        action "你输入不符合规范,请输入0-4数字!" /bin/false
        #跳出本次循环,继续下一次的循环
        continue
    fi
    #根据菜单列表进行选择要管理的主机
    case $Num in
        0)
            clear
            Menu
            ;;
        1)
            action "即将连接lb01主机!" /bin/true
            ping -c1 -W1 172.16.1.5 &>/dev/null
            if [ $? -eq 0 ];then
                action "检测lb01主机网络连接正常!" /bin/true
                Port=$(nmap -p 22 172.16.1.5 |awk '/22/{print $2}')
                if [ $Port == "open" ];then
                    action "检测lb01主机22端口开放正常!" /bin/true
                    action "正在连接lb01主机...请等待..."
                    ssh -o StrictHostKeyChecking=no root@172.16.1.5
                else
                    action "失败:检测不到lb01主机的22端口,请检查再试!" /bin/false
                    continue
                fi
            else
                action "失败:检测不到lb01主机!" /bin/false
                continue
            fi
            ;;
        2)
            action "即将连接web01主机!" /bin/true
            ping -c1 -W1 172.16.1.7 &>/dev/null
            if [ $? -eq 0 ];then
                action "检测web01主机网络连接正常!" /bin/true
                Port=$(nmap -p 22 172.16.1.7 |awk '/22/{print $2}')
                if [ $Port == "open" ];then
                    action "检测web01主机22端口开放正常!" /bin/true
                    action "正在连接web01主机...请等待..."
                    ssh -o StrictHostKeyChecking=no root@172.16.1.7
                else
                    action "失败:检测不到web01主机的22端口,请检查再试!" /bin/false
                    continue
                fi
            else
                action "失败:检测不到web01主机!" /bin/false
                continue
            fi
            ;;
        3)
            action "即将连接db01主机!" /bin/true
            ping -c1 -W1 172.16.1.51 &>/dev/null
            if [ $? -eq 0 ];then
                action "检测db01主机网络连接正常!" /bin/true
                Port=$(nmap -p 22 172.16.1.51 |awk '/22/{print $2}')
                if [ $Port == "open" ];then
                    action "检测db01主机22端口开放正常!" /bin/true
                    action "正在连接db01主机...请等待..."
                    ssh -o StrictHostKeyChecking=no root@172.16.1.51
                else
                    action "失败:检测不到db01主机的22端口,请检查再试!" /bin/false
                    continue
                fi
            else
                action "失败:检测不到db01主机!" /bin/false
                continue
            fi
            ;;
        4)
            read -s -p "请输入退出jumpserver的密码:" Quit
            if [ $Quit == "gun" ];then
                action "好,我滚了,已经退出脚本!再见!" /bin/true
                exit
            else
                action "密码错误!请重新输入!" /bin/false
                continue
            fi
            ;;
        *)
            action "你输入不符合规范,请输入0-4数字!" /bin/false
            continue
    esac
done

3.执行结果

Shell脚本编程学习——循环语句之For循环【显哥出品,必为精品】

七、实现多级菜单

1.业务需求

主菜单 有退出脚本的功能

两个子菜单

执行脚本时,进入的是主菜单

根据主菜单进行选择进入子菜单

子菜单负责具体的命令

有返回上一级菜单的功能

2.脚本代码

[root@xian /server/scripts]# cat long_menu.sh 
#!/bin/bash
# File Name: long_menu.sh
# Author: lixian
#######################
#调用函数库
[ -f /etc/init.d/functions ] && source /etc/init.d/functions
#定义菜单
menu() {
cat<<EOF
+----------主菜单-----------+
|                           |
|    1. 安装Nginx服务       |
|                           |
|    2. 安装PHP服务         |
|                           |
|    3. 退出脚本            |
|                           |
+---------------------------+
EOF
}
Nginx_menu(){
cat<<EOF
+-------安装Nginx服务-------+
|                           |
|    1. 安装Nginx-1.16版本  |
|                           |
|    2. 安装Nginx-1.18版本  |
|                           |
|    3. 返回上一级菜单      |
|                           |
+---------------------------+
EOF
}
PHP_menu(){
cat<<EOF
+--------安装PHP服务--------+
|                           |
|    1. 安装PHP-5.6版本     |
|                           |
|    2. 安装PHP-5.7版本     |
|                           |
|    3. 返回上一级菜单      |
|                           |
+---------------------------+
EOF
}

while true
do
    menu
read -p "请根据菜单输入你需要操作的选项:" Install
case $Install in
    1)
        echo "安装Nginx服务版本菜单:"
        while true
        do
            Nginx_menu
            read -p "请输入你需要安装nginx服务的版本:" Install_Nginx
            case $Install_Nginx in
                1)
                    echo "正在安装nginx-1.16版本。。。"
                    sleep 5
                    echo "安装成功"
                    ;;
                2)
                    echo "正在安装nginx-1.18版本。。。"
                    sleep 5
                    echo "安装成功"
                    ;;
                3)
                    echo "返回上一级菜单"
                    break
                    ;;
                *)
                    echo "错误:请输入正确的选项" 
            esac
            done
            ;;
    2)
        echo "安装PHP服务版本菜单:"
        while true
        do
            PHP_menu
            read -p "请输入你需要安装PHP服务的版本:" Install_PHP
            case $Install_PHP in
                1)
                    echo "正在安装php-5.6版本。。。"
                    sleep 5
                    echo "安装成功"
                    ;;
                2)
                    echo "正在安装php-5.7版本。。。"
                    sleep 5
                    echo "安装成功"
                    ;;
                3)
                    echo "返回上一级菜单"
                    break
                    ;;
                *)
                    echo "错误:请输入正确的选项" /bin/false
            esac
        done
        ;;
    3)
        action "退出脚本成功!" /bin/true
        exit
        ;;
    *)
        echo "您输入的选项有误!请重新输入!"
        ;;

esac
done

3.执行结果

[root@xian /server/scripts]# sh long_menu.sh 
+----------主菜单-----------+
|                           |
|    1. 安装Nginx服务       |
|                           |
|    2. 安装PHP服务         |
|                           |
|    3. 退出脚本            |
|                           |
+---------------------------+
请根据菜单输入你需要操作的选项:1
安装Nginx服务版本菜单:
+-------安装Nginx服务-------+
|                           |
|    1. 安装Nginx-1.16版本  |
|                           |
|    2. 安装Nginx-1.18版本  |
|                           |
|    3. 返回上一级菜单      |
|                           |
+---------------------------+
请输入你需要安装nginx服务的版本:2
正在安装nginx-1.18版本。。。
安装成功
+-------安装Nginx服务-------+
|                           |
|    1. 安装Nginx-1.16版本  |
|                           |
|    2. 安装Nginx-1.18版本  |
|                           |
|    3. 返回上一级菜单      |
|                           |
+---------------------------+
请输入你需要安装nginx服务的版本:3
返回上一级菜单
+----------主菜单-----------+
|                           |
|    1. 安装Nginx服务       |
|                           |
|    2. 安装PHP服务         |
|                           |
|    3. 退出脚本            |
|                           |
+---------------------------+
请根据菜单输入你需要操作的选项:3
退出脚本成功!                                             [  成功  ]

本站博主 , 版权所有丨如未注明 , 均为原创
转载请注明原文链接:Shell脚本编程学习——循环语句之For循环【显哥出品,必为精品】
喜欢 (1)

您必须 登录 才能发表评论!

(1)个小伙伴在吐槽
  1. I may need your help. I've been doing research on gate io recently, and I've tried a lot of different things. Later, I read your article, and I think your way of writing has given me some innovative ideas, thank you very much.
    gate.io2023-05-26 01:49