Shell函数与数组

Posted

tags:

篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了Shell函数与数组相关的知识,希望对你有一定的参考价值。

1、什么是函数

  被命名的语句块儿;有开始和结束的边界;

  begin ...... end

2、Shell语句中的语句块儿

  (1)、(语句1;语句2;...)

  (2)、{语句1;语句2;...}

  (3)、if else elif while for

  (4)、被命名的语句块儿,函数;

3、Shell函数的定义

  函数的要素:(1)、函数名称 (2)、语句块儿 (3)、返回值 (4)、参数

  Shell函数定义2种基本格式:

(1)

function 函数名称(){

  $1

  //若干语句

}

返回值类型:是一个整型量,该整型量在函数调用结束时,保存在$?环境变量中;

参数:是通过位置变量进行参数传递的。

定义函数,是不会执行函数中的语句的,只有其后的调用函数,才会执行,在Shell中,用函数名称直接调用。

#!/bin/bash

function show(){
    echo "Hello"
}

show

技术分享

(2)

函数名称(){

  //若干语句

}

#!/bin/bash

show(){
    echo "Hello"
}

show

技术分享

4、Shell函数的调用

  Shell函数调用与命令的调用方式一样,当编写一个函数之后,该函数相当于Shell的一个内部命令。

注意:

  (1)、函数必须先定义后调用,因为Base是逐行解析和执行的;

  (2)、写函数最好:将所有的函数定义写在最前,其中没有任何命令的执行,将所有的被执行的命令书写在整个Shell文件的后半部分。

  (3)、Shell在执行一个命令行时,首先在Shell进程所管理的函数表中查询有没有该名称的函数,如果有,则调用该函数,如果没有,则寻找内部命令,找到则执行,如果内部命令也没有找到,则在PATH环境变量中寻找对应的外部命令,找到则执行,如果还没有找到,则报错command not found;

  (4)、编写Shell脚本定义函数时,不能和内部命令或外部命令重名。

5、变量作用域

  变量的作用域指的是变量能够起作用的范围;

  Shell脚本中任何一个位置赋予一个变量,它就是用户变量,用户变量在整个Shell进程中是全局有效的;换句话说,对于Shell中直接定义的变量,都可以认为是全局变量,但是需要注意执行顺序;

  全局变量将导致很多运行函数的运行特性发生变化;为此,解决方案如下:

(1)、使用bash提供的特性,这个特性是bash内部命令local提供的,在函数体里面定义变量时,在变量前增加local命令,可以使得该变量只在函数中起作用;不在是一个用户变量,而是一个Bash中的局部变量。bash的内部命令local只能在函数定义体中使用。

#!/bin/bash

Hello(){
    local userName=madong
    echo $userName
}

echo "Before Hello : " $userName
Hello
echo "After Hello : " $userName

技术分享

6、Shell数组

(1)、格式 : Shell数组的定义需要使用特殊符号 : ()

变量名称=(字符串1 字符串2 字符串3 .....)

变量名称=([下标索引]=字符串1,   ...)

(2)、根据下标寻找数组元素

${数组变量名称[下标]} ; 下标从0开始;

技术分享

(3)、数组上的一些操作

i>获得数组所有元素:${数组变量名称[*]} ;  ${数组变量名称[@]}

技术分享

ii>获取数组长度 : ${#数组变量名称[*]} ;  ${#数组变量名称[@]}

技术分享

iii>数组遍历:通过下标的方式遍历数组,但是有局限性,如果被遍历数组下标索引是非连续的,那么这种遍历方式就会失效。

遍历代码:

#!/bin/bash

index=0
erray=(abc def ghi lmn opq rst)
while test $index -lt ${#array[*]}
do
    echo ${array[$index]}
    index=`expr $index + 1`
done

技术分享

通过for循环直接遍历

#!/bin/bash

array=(abc def xyz)
for var in ${array[*]}
do
    echo $var
done

技术分享

Shell数组定义时用() ; 使用时用{} ;

7、一些更灵活的使用

(1)、数组的截取  : 找下标连续的子集

${数组变量名称[@]:起始下标}    #从起始下标开始,截取出其余所有元素组成一个新数组;

技术分享

${数组变量名称[@]:起始下标:长度}  #从起始下标开始,截取长度个元素构成一个新数组;

技术分享

@符号也可以换成*

(2)、修改数组元素的值和数组元素个数

i>数组名称[下标]=字符串

如果下标的值大于数组当前元素个数,则会将数组下标索引范围扩大,然后为数组添加一个新元素。

数组元素个数:数组中非空字符串元素个数

(3)、删除数组,格式:

数组名称[下标]=""   #并没有真正的删除数组元素,而只是将数组元素的值清空,数组元素个数不变;

unset 数组名称[下标]  #彻底删除了数组元素,数组元素个数会减少;

注意:都不会使得被删除元素其后的元素自动的向前挪动;

推论:Shell数组元素的下标可以是不连续的,甚至可以在定义数组的时候,其下标索引就是不连续的,

8、Shell编程实现学生信息管理

  实现最简单的输入,和保存文件功能:

#!/bin/bash

if ! [ -e ./stdData.txt ]
then
    echo "学生姓名 学生年龄 学生性别 学生邮箱" >> ./stdData.txt
    echo "-----------------------------------" >> ./stdData.txt
fi

stdName=""
stdAge=""
stdSex=""
stdMail=""

while test 1 -eq 1
do
    read -p "Please input student name : " stdName

    stdNameLength=`expr length "$stdName"`

    if test $stdNameLength -lt 10 -a $stdNameLength -gt 0
    then
        break
    else
        echo "Input ERROE"
    fi  
done    

while test 1 -eq 1
do
    read -p "Please input student age : " stdAge

    if test $stdAge -gt 10 -a $stdAge -lt 18
    then
        break
    else
        echo "Input ERROE"
    fi
done

while test 1 -eq 1
do
    read -p "Please input student sex(f:女 m:男) : " stdSex

    if test $stdSex = f -o $stdSex = m
    then
        break
    else
        echo "Input ERROE"
    fi
done

while test 1 -eq 1
do
    read -p "Please input student mail : " stdMail
    stdMailLength=`expr length "$stdMail"`

    if test $stdMailLength -gt 10
    then
        break
    else
        echo "Input ERROE"
    fi
done

echo $stdName $stdAge $stdSex $stdMail >> ./stdData.txt

技术分享

在文件中查询结果:

技术分享


本文出自 “11586096” 博客,请务必保留此出处http://11596096.blog.51cto.com/11586096/1847073

以上是关于Shell函数与数组的主要内容,如果未能解决你的问题,请参考以下文章

Shell ❀ 函数与数组

shell函数与数组

shell_数组与字符串

18 shell脚本--009数组与字符串

201555332盛照宗—网络对抗实验1—逆向与bof基础

shell编程函数与数组