驽马十驾 驽马十驾

驽马十驾,功在不舍

目录
shell函数中不同于现代化编程语言的一些坑
/  

shell函数中不同于现代化编程语言的一些坑

Shell 的函数就是一个大坑,坑的人不要不要的。

函数形参

不同于目前流行的Java等语法,shell 的方法形参的传入和调用都有些不明了,就没有人去改良下吗?

定义一个方法可以有很多种,但是通常都用的是最简洁的,直接一个方法名。

hello(){
	echo "hello"
}

假如我需要定义一个形参,比如将姓名传入进去,传统的语法可能是这样的,但是实际 shell 用的是下面这种

# 错误写法
hello(name){
	echo "hello $name"
}

#正确写法
hello(){
	echo "hello $1"
}

其中$1表示的就是传入的第一个参数,$2表示第二个参数,依次类推哈。

那么调用的时候也是很奇葩的用法

  • 强制:不要在函数名后加(),只需要方法名,然后参数通过空格区分。
  • 建议:通过$(method),将函数包裹起来,表明这一行是函数执行。
hello "mark"

函数返回值

shell 中函数的返回值只能是数值类型,是的,你没有看错就是数值类型,当你返回字符串的时候,会报错: return: xxx: numeric argument required

a(){
  return "ab"
}

b(){
	return "123"
	#return 123 这个写法也可以
}

#调用a,报错:ab: numeric argument required
$(a)
#调用 b,成功
$(b)

你如果要问我假就是要返回字符串了?有 2 个办法:

  • 使用全局变量来代替吧。
a(){
  name="ab"
}

# 直接调用全局变量 $name
echo "name:$name"
  • 通过$(method)来接收函数中的输出
a(){
  echo "ab"
}

# 执行该操作后的值就是 ab
re=$(a)
echo "name:$re"

函数调用

上文已经提到过了,函数的返回值只能是数值,那么我们通过如下方法来接收来打印,你会发现输出为空。呵呵...

sum(){
  return "5"
}
b=sum
echo "b:$b"

此时你一打印会发现结果是b:sum。此时问题出在你调用方式不对,shell中如要要获取函数执行后的某个结果(具体后面谈),应该通过$(method)这种方式进行调用后赋值。

b=$(sum)

此时假如执行,你会发现执行的结果是b: 是的,什么都没有。

原因是通过b=$(sum)获取的是函数sum的标准输出,说人话就是类似echo在控制台的输出内容,我们可以测试下:

sum(){
	echo 667 #1
  return "5"
}
# 通过$(method)调用
b=$(sum)
echo "b:$b"

结果只有一行,只是b:667,并没有#1处的输出,这里后面讲

b:667

那么如何获取正常的返回值了?利用$?这个来获取上一个指令的执行结果。

sum(){
  return "5"
}
sum
echo "b:$?"

此时结果就是

b:5

这下我们来测试下共同使用

sum(){
  echo 6
  return "5"
}
a=$(sum)
echo "b:$?"
echo "a:$a"

结果就是

b:5
a:6

这里 a表示的就是 sum函数中所有面向控制台的输出,注意是所有,比如这个方法

# 方法
sum(){
  echo 6
  echo "i love wmm"
  echo "i love kotlin"
  return "5"
}
a=$(sum)
echo "$a"

#输出结果是
6
i love wmm
i love kotlin

总结

  • 函数的参数不需要显示声明,需要传递参数的时候,写在函数名的后面,多个参数值通过空格分开
  • 函数体中,如果需要使用参数,通过$0-$n来调用。
  • 函数的返回值只能是数值类型,不能是字符串类型。
  • 调用函数时,如果不需要返回值,那么只需要method [param]即可。
  • 将函数调用后赋值给a,其表示的函数的意义是函数执行过程中的标准输出,如果要获取返回值需要通过$?
  • 调用函数时,如果需要函数的标准输出内容,那么需要通过$(method)进行标准输出的接收,此时函数中的标准输出就不会打印到控制台,而是赋值到变量中了

$?表示的含义其实是上一次命令的返回值,所以假如要获取返回值,一定要在函数执行的下一行使用该变量

re=$(method) 该调用会将函数中本身的控制台输出吃掉,然后复制给参数re

骐骥一跃,不能十步。驽马十驾,功在不舍。