高级shell脚本编程笔记第一章——创建自己的函数、函数库以及下载、安装、使用GUN shoot shell脚本函数库的方法

目录

1、基本的脚本函数

1.1、创建函数

1.2、使用函数

2、返回值

2.1、默认退出状态码

2.2、使用return命令

2.3、使用函数输出

3、在函数中使用变量

3.1、向函数传递参数

3.2、在函数中处理变量

4、数组变量和函数

4.1、向函数传数组参数

4.2、从函数返回数组

5、函数递归

6、创建库

7、在命令行上使用函数

7.1、在命令行上创建函数

7.2、在.bashrc文件中定义函数

7.2.1、直接定义函数

7.2.2、读取函数文件

8、下载、安装、使用GUN shoot shell脚本函数库

8.1、下载及安装

8.2构建库

8.3shtool库函数

8.4使用库


 完整笔记请前往此处获取:https://download.csdn.net/download/qq_55908180/88366003

1、基本的脚本函数

函数是一个脚本代码块,你可以为其命名并在代码中任何位置重用。要在脚本中使用该代码块时,只要使用所起的函数名就行了(这个过程称为调用函数)。

1.1、创建函数

在bash shell 脚本中有两种格式可以用来创建函数。

第一种格式使用关键字function,后跟分配给该代码块的函数名:

function name{

       commands

}

name属性定义了赋予函数的唯一名称。脚本中定义的每个函数都必须有一个唯一的名称。commands是构成函数的一条或多条bash shell命令。在调用该函数时,bash shell会按命令在函数中出现的顺序依次执行、就像在普通脚本中一样。

第二种格式是更接近于其他语言的定义函数方式:

name() {

       commands

}

1.2、使用函数

想在脚本中使用函数,只需要像其他shell命令一样,在行中指定函数名就行了。如:

#!/bin/bash

function func1 {

		echo "This is an example of a function"
}

count=1
while [ $count -le 5 ]
do
		func1
		count=$[ $count + 1 ]
done
echo "This is the end of the loop"
func1
echo "Now this is the end of the script"

 注意:函数定义不一定非得是shell脚本中首先要做的事,如果在函数被定义前使用函数,就会收到错误消息。如:

#!/bin/bash

function func1 {

		echo "This is an example of a function"
}

count=1
while [ $count -le 5 ]
do
		func1
		count=$[ $count + 1 ]
done
echo "This is the end of the loop"
func2
echo "Now this is the end of the script"

function func2 {
		echo "This is an example of a function"
}

 注意:函数名必须是唯一的,否则也会有问题。如果你重定义了函数,新定义会覆盖原来函数的定义,并且这一切不会产生任何错误消息。如:

#!/bin/bash

function func1 {

		echo "This is the first definition of the function name"
}

func1

function func1 {
	echo "This is a repeat of the same function name"
}
func1
echo "This is the end of the script"

2、返回值

bash shell会把函数当作一个小型脚本,运行结束时会返回一个退出状态码。有3种不同的方法来为函数生成退出状态码。

2.1、默认退出状态码

默认情况下,函数的退出状态码是函数中最后一条命令返回的退出状态码,在函数执行结束后,可以用标准变量$?为函数生成退出状态码。如:

#!/bin/bash

func1() {
		echo "trying to display a non-existent file"
		ls -l badfile
}
echo "testing the function: "
func1
echo "The exit status is: $?"

 下面的例子可以知道函数中其他的命令是否成功运行,如:

#!/bin/bash

func1() {
		ls -l badfile
		echo "This was a test of a bad command"
}
echo "testing the function: "
func1
echo "The exit status is: $?"

注意:使用函数的默认退出状态码是很危险的。不过好在有几种办法可以解决这个问题。

2.2、使用return命令

return命令允许指定一个整数值来定义函数的退出状态码,从而提供了一种简单的途径来编程设定函数退出状态码。如:

#!/bin/bash

function db1 {
	read -p "Enter a value: " value
	echo "doubling the value"
	return $[ $value * 2 ]
}
db1
echo "The new value is $?"

db1函数会将$value变量中用户输入的值翻倍.然后用return命令返回结果。脚本用s ?变量显示了该值。

但当用这种方法从函数中返回值时,要小心了。记住下面两条技巧来避免问题:

1、函数一结束就取返回值;

2、退出状态码必须是0~255。如果退出状态码大于256,都会随机生成一个错误值如:

2.3、使用函数输出

获得任何类型的函数输出,并将其保存到变量中。

result=’dbl’

这个命令会将dbl函数的输出赋给$result变量。如:

#!/bin/bash

function dbl {
	read -p "Enter a value: " value
	echo $[ $value * 2 ]
}
result=$(dbl)
echo "The new value is $result"

3、在函数中使用变量

在上面的例子中用来一个叫$value的变量来保存处理后的值。在函数中使用变量时,一定要注意它们的定义方式以及处理方式,这是常见错误的根源

3.1、向函数传递参数

函数可以使用标准的参数环境变量来表示命令行上传给函数的参数,也可以用特殊变量s#来判断传给函数的参数数目。

在脚本中指定函数时,必须将参数和函数放在同一行,如:  func1 $value 10

#!/bin/bash

function addem {
		if [ $# -eq 0 ] || [ $# -gt 2 ]
		then 
				echo -1
		elif [ $# -eq 1 ]
		then
				echo $[ $1 + $1 ]
			else
					echo $[ $1 + $2 ]
			fi
}

echo -n "Adding 10 and 15: "
value=$(addem 10 15)
echo $value
echo -n "Let's try adding just one number: "
value=$(addem 10)
echo $value
echo -n "Now trying adding no numbers: "
value=$(addem)
echo $value
echo -n "Finally, try adding three numbers: "
value=$(addem 10 15 20)
echo $value

注释:首先,addem函数会检查脚本传给它的参数数目。如果没有任何参数,或者参数多于两个,会返回值-1。如果只有一个参数,addem会将参数与自身相加。如果有两个参数,addem会将它们进行相加。

由于函数使用特殊参数环境变量作为自己的参数值,因此它无法直接获取脚本在命令行中的参数值。要在函数中使用这些值,必须在调用函数时手动将它们传过去。如:

#!/bin/bash

function func1 {
	echo $[ $1*$2 ]
}
if [ $# -eq 2 ]
then
		value=$(func1 $1 $2)
		echo "This result is $value"
else
		echo "Usage: badtest1 a b"
fi

3.2、在函数中处理变量

函数使用两种类型的变量:全局变量局部变量

1、全局变量

在脚本的任何地方都有效的变量。默认情况下,在脚本中定义的任何变量都是全局变量。在函数外定义的变量可在函数内正常访问。如:

#!/bin/bash

function dbl {
		value=$[ $value * 2 ]
}
read -p "Enter a value: " value
dbl
echo "The new value is: $value"

2、局部变量

只要在变量声明的前面加上local关键字就可以把函数内部使用的任何变量都声明成局部变量。local temp

也可以在变量赋值语句中使用local关键字:local temp=$[ $value + 5 ]

local关键字保证了变量只局限在该函数中。如果脚本中在该函数之外有同样名字的变量,那么shell将会保持这两个变量的值是分离的。现在你就能很轻松地将函数变量和脚本变量隔离开了,只共享需要共享的变量。如:

#!/bin/bash

function func1 {
		local temp=$[ $value + 5 ]
		result=$[ $temp * 2 ]
}
temp=3
value=9
func1
echo "The result is $result"
if [ $temp -gt $value ]
then
		echo "temp is lager"
else
		echo "temp is smaller"
fi

4、数组变量和函数

4.1、向函数传数组参数

把数组变量当做单个参数传递的话,会不起作用。如:

#!/bin/bash

function test {
		echo "The parameters are: $@"
		thisarray=$1
		echo "The received array is: ${thisarray[*]}"
}

myarray=(1 2 3 4 5 )
echo "The original array is: ${myarray[*]}"
test $myarray

如果试图将该数组变量作为函数参数,函数只会取数组变量的第一个值。

要解决这个问题,就要把该数组变量的值分解成单个的值,然后将这些值作为函数参数使用。在函数内部,可以将所有的参数重新组合成一个新的变量。下面是个具体的例子。

#!/bin/bash

function addarray {
		local sum=0
		local newarray
		newarray=($(echo "$@"))
		for value in ${newarray[*]}
		do
				sum=$[ $sum + $value ]
		done
		echo $sum
}

myarray=(1 2 3 4 5)
echo "The original array is: ${myarray[*]}"
arg1=$(echo ${myarray[*]})
result=$(addarray $arg1)
echo "The result is $result"

4.2、从函数返回数组

从函数里向shell脚本传回数组变量也用类似的方法。函数用echo语句来按正确顺序输出单个数组值,然后脚本再将它们重新放进一个新的数组变量中。如:

#!/bin/bash

function array1 {
		local origarray
		local newarray
		local elements
		local i
		origarray=($(echo "$@"))
		newarray=($(echo "$@"))
		elements=$[ $# - 1 ]
		for ((i=0;i<= $elements;i++))
				{
						newarray[$i]=$[ ${origarray[$i]} * 2 ]
				}
				echo ${newarray[*]}
}

myarray=(1 2 3 4 5 )
echo "The original array is: ${myarray[*]}"
arg1=$(echo ${myarray[*]})
result=($(array1 $arg1))
echo "The new array is: ${result[*]}"

5、函数递归

首先说一下什么是函数递归:函数递归是指一个函数在执行的过程中调用了自己。它可以用于解决需要重复执行同一操作的问题,以及涉及到数学和计算机科学中的问题。递归函数必须包含一个基础案例,以避免无限递归。

局部函数变量的一个特性是自成体系。除了从脚本命令行处获得的变量,自成体系的函数不需要使用任何外部资源。

递归算法的经典例子是计算阶乘。下面例子给出一个简单的递归计算一个数的阶乘的例子。如:

#!/bin/bash

function factorial {
		if [ $1 -eq 1 ]
		then
				echo 1
		else
				local temp=$[ $1-1 ]
				local result=$(factorial $temp)
				echo $[ $result * $1 ]
		fi
}

read -p "Enter value: " value
result=$(factorial $value)
echo "The factorial of $value is: $result"

6、创建库

为了避免同一段代码在多个脚本中都要重复使用,而每一次都要定义。创建函数库文件就显得很重要。如:下面创建了一个脚本中所需的函数的公用库文件。

如果尝试像普通脚本一样运行库文件,函数并不会出现在脚本中。如:

使用函数库的关键在于source命令。source命令会在当前shell上下文中执行命令,而不是创建一个新shell。可以用source命令来在shell脚本中运行库文件脚本。这样脚本就可以使用库中的函数了。

source命令有个快捷的别名,叫作点操作符( dot operator )。要在shell脚本中运行myfuncs库文件、只需添加下面这行: . ./myfuncs

如:

 

7、在命令行上使用函数

一旦在shell中定义了函数,就可以在整个系统中使用它了,无需担心脚本是不是在PATH环境变量里。重点在于让shell能够识别这些函数。有几种方法可以实现。

7.1、在命令行上创建函数

因为shell会解释用户输入的命令,所以可以在命令行上直接定义一个函数。有两种方法。一种方法是采用单行方式定义函数。如:

注意:当在命令行上定义函数时,你必须记得在每个命令后面加个分号,这样shell就能知道在哪里是命令的起止了。如:

另一种方法是采用多行方式来定义函数。在定义时,bash shell会使用次提示符来提示输入更多命令。用这种方法,你不用在每条命令的末尾放一个分号,只要按下回车键就行。如:

7.2、在.bashrc文件中定义函数

在命令行上直接定义shell函数的明显缺点是退出shell时,函数就没有了。对于复杂的函数来说,下一次还要重新定义。

有一个非常简单的方法是将函数定义在一个特定的位置,这个位置在每次启动一个新shell的时候,都会由shell重新载入。

7.2.1、直接定义函数

可以直接在主目录下的.bashrc文件中定义函数,但是注意,不要删除该文件里的东西,直接把要加的函数放在文件末尾就行了。如:

# .bashrc

if [ -r /etc/bashrc ]; then
		. /etc/bashrc
fi
function addem{
	echo $[ $1 + $2 ]
}

该函数会在下次启动新bash shell时生效。随后你就能在系统上任意地方使用这个函数了。

7.2.2、读取函数文件

只要是在shell脚本中,都可以用source命令(或者它的别名点操作符)将库文件中的函数添加到你的.bashrc脚本中。

# .bashrc

if [ -r /etc/bashrc ]; then
		. /etc/bashrc
fi

. /home/txf/shell/myfuncs

注意红色框:库文件的路径名一定要正确,这样shell才能找到该文件。加好之后重启一下命令行,就可以直接调用了。

8、下载、安装、使用GUN shoot shell脚本函数库

shtool提供了一些简单的shell脚本函数,可以用来完成日常的shell功能。

8.1、下载及安装

下载地址:https://mirrors.aliyun.com/gnu/shtool/

使用tar命令提取文件

tar -zxvf shtool-2.0.8.tar.gz

8.2构建库

shtool文件必须针对特定的Linux环境进行配置。配置工作必须使用标准的configuremake命令,这两个命令常用于C编程环境。要构建库文件,只要输入:

configure命令会检查构建shtool库文件所必需的软件。一旦发现了所需的工具,它会使用工具路径修改配置文件。

make命令负责构建shtool库文件。最终的结果( shtool )是一个完整的库软件包。你也可以使用make命令测试这个库文件。

使用make命令的install选项就可以将库安装到Linux系统中的公用位置,这样所有的脚本就都能够使用这个库了。

8.3shtool库函数

shtool库提供了大量方便的、可用于shell脚本的函数。

每个shtool函数都包含大量的选项和参数,你可以利用它们改变函数的工作方式。下面是shtool函数的使用格式:

shtool [ options] [ function [options] [args ] ]

8.4使用库

可以在命令行或自己的shell脚本中直接使用shtool函数。下面是一个在shell脚本中使用platform函数的例子。

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

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

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

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值