前往小程序,Get更优阅读体验!
立即前往
首页
学习
活动
专区
工具
TVP
发布
社区首页 >专栏 >Golang 语言函数的高级使用方式

Golang 语言函数的高级使用方式

作者头像
frank.
发布2021-11-30 09:24:52
5990
发布2021-11-30 09:24:52
举报
文章被收录于专栏:Golang语言开发栈

01 介绍

在 Golang 语言中,除了 main 和 init 函数之外,其他函数还可以接收一个或多个参数,并且 Golang 函数可以接收可变长度的参数,需要注意的是,当 Golang 函数接收可变长度的参数时,需要将可变长度参数放在所有接收参数的最后,实际上,可变长度参数是一个切片类型的参数。

Golang 语言中的函数还可以接收多个返回值,通常会用于返回 error 错误信息。

Golang 语言的函数是第一公民「first-class」,它允许函数赋值给变量,作为参数传递给其他函数,或从其他函数返回。

本文我们介绍 Golang 语言函数的高级使用方式,关于函数的基本使用方式,我们在之前的文章中已经介绍过,本文不再赘述。

02 匿名函数

所谓匿名函数,顾名思义就是没有定义函数名的函数,通常用于只需短期使用的函数。我们还可以将匿名函数赋值给一个变量,通过变量调用匿名函数。我们通过以下示例代码,演示匿名函数的使用方式。

匿名函数 - 无参数和返回值:

代码语言:javascript
复制
func TestAnonymous(t *testing.T) {
 func () {
  t.Log("Hello World")
 }()
}

匿名函数 - 有参数和返回值:

代码语言:javascript
复制
func TestAnonymous(t *testing.T) {
 func (a, b int) int {
  return a + b
 }(1,2)
}

匿名函数 - 赋值给变量:

代码语言:javascript
复制
func TestAnonymous(t *testing.T) {
 sum := func (a, b int) int {
  return a + b
 }
 t.Log(sum(1, 2))
}

03 闭包

在 Golang 语言中,函数支持匿名函数,闭包就是一种特殊的匿名函数,它可以用于访问函数体外部的变量。

示例代码:

代码语言:javascript
复制
func TestClosures(t *testing.T) {
 x, y := 1, 2
 func (a, b int) {
  t.Log(a + b)
 }(x, y)
}

需要注意的是,在 for ... range ... 中,使用协程执行闭包时,经常会掉「坑」。因为匿名函数可以访问函数体外部的变量,而 for ... range ... 返回的 val 的值是引用的同一个内存地址的数据,所以匿名函数访问的函数体外部的 val 值会是循环中最后输出的一个值。

示例代码:

代码语言:javascript
复制
func TestClosures(t *testing.T) {
 values := []int{1,2,3,4,5}
 for _, val := range values {
  go func() {
   t.Logf("%p %d\n", &val, val)
  }()
 }
 time.Sleep(time.Second)
}

避「坑」的方法是使用闭包函数传递参数,示例代码如下:

代码语言:javascript
复制
func TestClosures(t *testing.T) {
 values := []int{1,2,3,4,5}
 for _, val := range values {
  go func(val int) {
   t.Logf("%p %d\n", &val, val)
  }(val)
 }
 time.Sleep(time.Second)
}

04 递归

在 Golang 语言中,也支持递归函数。需要注意的是,使用闭包递归,需要在定义闭包之前,显式声明闭包。

示例代码:

代码语言:javascript
复制
func TestRecursion(t *testing.T) {
 var fib func(n int) int
 fib = func (n int) int {
  if n < 2 {
   return n
  }
  return fib(n - 1) + fib(n -2)
 }
 t.Log(fib(7))
}

05 自定义函数类型

在 Golang 语言中,我们也可以像定义结构体类型一样,定义函数类型。

示例代码:

代码语言:javascript
复制
type sum func(int, int) int

自定义的函数类型,可以作为高阶函数的参数或返回值。

06 高阶函数

高阶函数是接收参数或返回值是函数类型的变量的函数,也就是说高阶函数是操作其他函数的函数。

函数作为参数:

代码语言:javascript
复制
func TestHigherOrder(t *testing.T) {
 t.Log(operation(1, 2, func(x, y int) int {
  return x + y
 }))
}

func operation(x, y int, operaFuc func(int, int) int) int {
 rst := operaFuc(x, y)
 return rst
}

函数作为返回值:

代码语言:javascript
复制
func TestHigherOrder(t *testing.T) {
 sum := operation1()
 t.Log(sum(2, 3))
}

func operation1() func(x, y int) int {
 sum := func(x, y int) int {
  return x + y
 }
 return sum
}

07 总结

本文我们介绍了 Golang 语言中函数的高级使用方式,包含匿名函数、闭包、递归、自定义函数类型和高阶函数,并分别列举了一个简单示例,感兴趣的读者朋友,可以在本地运行示例代码,并通过修改调式代码,加深理解。

参考资料: https://gobyexample.com/closures https://gobyexample.com/recursion https://zetcode.com/golang/function/ https://golangbot.com/first-class-functions/ https://www.golangprograms.com/go-language/functions.html https://golangbyexample.com/function-golang-complete-guide/

本文参与 腾讯云自媒体同步曝光计划,分享自微信公众号。
原始发表:2021-11-21,如有侵权请联系 cloudcommunity@tencent.com 删除

本文分享自 Go语言开发栈 微信公众号,前往查看

如有侵权,请联系 cloudcommunity@tencent.com 删除。

本文参与 腾讯云自媒体同步曝光计划  ,欢迎热爱写作的你一起参与!

评论
登录后参与评论
0 条评论
热度
最新
推荐阅读
领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档