04-Shell编程之四

本文介绍了Shell编程中的流程控制语句,包括if/then、if/then/else、if/then/elif/then/else和case语句,详细讲解了其语法结构和示例。此外,还探讨了for循环语句的使用,以及如何在Shell脚本中定义和应用函数,以提高代码复用性。

摘要生成于 C知道 ,由 DeepSeek-R1 满血版支持, 前往体验 >

4、流程控制语句和函数

4.1   条件语句

简单的shell脚本从头到尾可以执行命令的集合,而条件语句允许用户在shell脚本中实现当满足条件时执行。

包括if/thenif/then/elseif/then/elif/then/elsecase语句等。

 

if/then语句语法结构:

 

  if <条件>;then

      <命令1>

       <命令2>

         ……

  fi

示例:
  systemctl is-active psacct  >/dev/null
  if  [ $? –ne 0 ];then
     systemctl start psacct
 fi

shell程序中的条件分支是通过if条件语句来实现的,其一般格式为:

  if条件命令串

  then

  条件为真时的命令串

  else

  条件为假时的命令串

  fi

 

If语句语法(bashpdksh

  if (表达式1) then

  命令

  elif (表达式2) then

  命令

  else

  命令

  fi

 

elifelse条件语句都是if语句的可选部分,elifelse if的缩写。

 

If语句语法(tcsh

  if (表达式1) then

  命令

  else if (表达式2) then

  命令

  else

  命令

  endif

 

举例

  if [-f .profile]

  then

  echo “there is a .profile file in the current directory.”

  else

  echo “could not find the .profile file.”

  fi


if/then/else语句:                                                                          

语法结构:

if/then/else语句

    if <条件>then

        <命令1>

       else

        <命令2>

fi


if/then/elif/then/else语句: 

(继续扩展,用于测试多个条件)

语法结构:

    if <条件1>then

        <命令1>

   elif<条件2>; then

        <命令2>

    else

        <命令3>

    fi


示例1:
  systemctl is-active psacct  >/dev/null
  if  [ $? –ne 0 ];then
        systemctl start psacct
     else
        systemctl stop psacct
 fi

示例2:
  systemctl is-active httpd  >/dev/null
  HTTPD_ACTIVE=$?
  systemctl is-active mariadb >/dev/null
  MARIADB_ACTIVE=$?
     if  [ “$HTTPD_ACTIVE” –eq 0 ];then
          systemctl start httpd
          elif [ “$MARIADB_ACTIVE” –eq 0 ];then
                  systemctl start mariadb 
      else
                   echo “the httpd and mariadb is error”
      fi

case语句

if/then/elif/then/else语句可以添加任意需要的条件去执行,但随着条件的增加,逻辑结构复杂不易理解,因此可以使用case语句。

 

语法结构:

 case <变量> in

        <1>

           命令1

            ;;

        <2>

           命令2

            ;;

  esac

if条件语句用于在两个选项中选定一项,而case条件选择为用户提供了根据字符串或变量的值从多个选项中选择一项的方法。
shell通过计算字符串string的值,将其结果依次和表达式exp-1、exp-2等进行比较,直到找到一个匹配的表达式为止,如果找到了匹配项则执行它下面的命令直到遇到一对分号(;;)为止。
在case表达式中也可以使用shell的通配符(“*”、“?”、“[ ]”)。通常用“*”作为case命令的最后表达式以便使在前面找不到任何相应的匹配项时执行“其他命令行”的命令。

举例:
此代码检查第一个命令行选项是-i还是-e。如果是-i,程序开始对以字母-i开头的第2个命令行选项所定义的文件中的行数进行计数。如果是-e,程序开始对以字母-e开头的第2个命令行选项所定义的文件中的行数进行计数。如果第1个命令行选项不是-e或-i,程序显示错误。
	case $1 in
		-i)
		count=‘grep ^i $2 | wc -l’
		echo “The number of lines in $2 that start with an I is $count”
		;;
		-e)
		count=‘grep ^e $2 | wc -l’
		echo “The number of lines in $2 that start with an e is $count”
		;;
		* )
		echo “That option is not recognized”
		;;
	esac
case语句示例:

 case “$1” in
        start)
           start
            ;;
        stop)
           stop
            ;;
         *)
           echo “Usage:$0(start|stop)”
 esac

4.2   for循环语句

       管理员在日常运维过程中,常常会遇到重复的任务,可能表现为对目标多次执行某个操作,比如10分钟内,每隔1分钟检查进程有无完成,也可能表现为一次对多个目标执行,那么此时用循环语句是合适的,其中for循环就是常见的一种循环结构。

for循环语法结构:

  for<变量> in <取值列表>;do

      <命令1>

       <命令2>

         ……

  done

for循环的一般格式为(bash和pkdsh):
  for 变量名
  [in数值列表]
  do 
  若干个命令行
  done
  变量名可以是用户选择的任何字符串,如果变量名是var,则在in之后给出的数值将顺序替换循环命令列表中的$var。如果省略了in,则变量var的取值将是位置参数。对变量的每一个可能的赋值都将执行do和done之间的命令列表。

在tcsh中,与for语句相同的是foreach语句,其一般格式为:
  foreach name (列表)
	命令
  end

实例
将任意数量的文本文件作为命令行选项。执行时,程序读取各个文件,将所有字符转换成大写,然后将结果存储在文件名相同而扩展名为.caps的文件中。

	for file
	do
	tr a-z A-Z < $file> $file.caps
	done
示例1:
 for HOST in host1 host2 host3;do
       echo “$HOST”
 done

示例2:
 for PACKAGE in $(rpm –qa kernel);do
       echo “$PACKAGE”was installed
 done

 

4.3   函数

shell脚本中,函数是一种隔离代码段的的方法,如果某个代码段经常需要被重复调用,可以使用函数实现,如代码需要更新,只需更新函数内容即可,所有引用函数的位置都会执行更新后的代码。

 

函数示例:

pathmunge ( ) {

    if [ “$2” = “after”];then

        PATH=$PATH:$1

       else

        PATH=$1:$PATH

    fi

}

函数定义
  在shell中还可以定义函数。函数实际上也是由若干条shell命令组成的,因此它与shell程序形式上是相似的,不同的是它不是一个单独的进程,而是shell程序的一部分。函数定义的基本格式为:
  functionname( )
  {
  	若干命令行
  }

调用函数的格式为:
  functionname [param1 param2……]

shell函数可以完成某些例行的工作,而且还可以有自己的退出状态,因此函数也可以作为if、while等控制结构的条件。
在函数定义时不用带参数说明,但在调用函数时可以带有参数,此时shell将把这些参数分别赋予相应的位置参数$1、$2、...及$*。

实例:
upper() {
	shift
	for I
	do
		tr a-z A-Z < $1 >$1.out
		rm $1
		mv $1.out $1
		shift
	done;
	}

lower() {
	shift
	for I
	do
		tr A-Z a-z < $1 > $1.out
		rm $1
		mv $1.out  $1
		shift
	done;
	}
if  [ “$EUID” = “0”];then
       pathmunge  /sbin
       pathmunge /usr/sbin
       pathmunge /usr/local/sbin
 else
       pathmunge  /usr/local/sbin  after
       pathmunge  /usr/sbin  after
       pathmunge  /sbin  after
 fi

 

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值