go语言函数、方法、闭包(详解)

本文涉及的产品
日志服务 SLS,月写入数据量 50GB 1个月
简介: go语言函数、方法、闭包(详解)

文章目录


前言


函数在数学中为两集合间的一种对应关系:输入值集合中的每项元素都能对应唯一一项输出值集合中的元素


在编程语言中函数为一类操作的集合体,具有一定的功能,有函数名、输入(参数)、输出(返回值)


一、什么是Go语言函数?


Go语言中支持多参数、多返回值


1.Go语言函数都包含什么?


函数声明


  func 函数名 (函数参数列表)(返回值类型){
    函数体
  }


函数参数


  值传递
  引用传递 
  函数可以作为另一个函数的实参进行回调


函数闭包(用于函数式编程,匿名函数)


  go编译器会对其进行识别,将闭包的变量存放在堆空间内
  并且闭包时不是返回了一个匿名函数,而是返回了一个结构体
  记录下函数返回地址和引用的环境中的变量地址
  同一个函数进行闭包,会因为环境变量的不同无法共享变量
  闭包函数内的变量进行改变会影响到当前所处的环境中的变量


函数方法


  函数方法要接收者函数,接收者函数可以是命名类型或者结构体类型的一个值或者一个指针。
  定义格式如下:
      接收者区域
    func(名称 类型)函数名()返回值类型{
      函数体
    }
  注意点:
    函数方法在执行时如果接收者是一个结构体,在函数内修改结构体数据,原结构体不会修改
    (会将结构体变量数据拷贝一份给和函数)
    如果是一个结构体指针,那么可以生效(直接将该结构体给函数)


2.简单的实现一个函数


代码如下(示例):


// 选最大值函数
//函数名
func maxs(a, b int) int {//括号内是参数列表,括号外int是返回值类型
  if a > b {
    return a
  } else {
    return b
  }
}


3.实现函数多参数


这里是在编写日志系统的时候写的一个输出日志的函数


代码如下(示例):


// 日志对象的方法,用于输出日志信息
//这里的args ...interface{}代表可以传任一个不同类型的参数
func (l LogGer) outLog(level logLevel, args ...interface{}) {
  if !l.eqLevel(level) {
    return
  }
  //看哪里调用这个函数了,哪里出错哪里调用,为了记录下出错的文件行号
  _, file, line, ok := runtime.Caller(2)
  file = strings.Split(file, "/")[len(strings.Split(file, "/"))-1]
  if !ok {
    return
  }
  filestr, _ := downloadLevel(level)
  fmt.Printf("[%s] [%s] [文件:%s] [行号:%d] 附加信息:", time.Now().Format("2006-01-02 15:03:04"), filestr, file, line)
  //对传进来的不定个参数进行解析
  for _, v := range args {
    fmt.Print(v)
  }
  fmt.Printf("\n")
}


4.实现函数多返回值


这里是在编写日志系统的时候写的一个输出日志的函数


代码如下(示例):


//返回int类型与错误类型
func judgeName(name string) (int, error) {
  if name=="jack"{
    return 0,nil
  }
  return -1, errors.New("传进来的不是jack")
}


二、什么是Go语言方法?


方法与函数有一定的区别,接口的话有所属的结构体作为接受者,相应的对象可以调用该方法,函数只实现了一定的功能,不能使用对象直接调用。


1.简单实现一个方法


代码如下(示例):


// 定义一个结构体并添加方法
type user struct {
  name        string
  age         int
  speak_array string
}
//属于结构体的方法
//这里的(Someone user)Someone是接受者名,user是类型还可以是user指针类型
func (Someone user) speak() {
  fmt.Printf("%s说:我今年%d岁,%s\n", Someone.name, Someone.age, Someone.speak_array)
}


二、什么是函数闭包?


func getSuperS() {
  //创建一个函数变量数组
  var temp [3]func() int
  j := 0
  for i := 0; i < 3; i++ {
    //直接使用当前所处环境中的j
    temp[i] = func() int {
      j++
      return j
    }
  }
  /*
    函数闭包使用的是该匿名函数所处环境的变量,如果变量重新声明
    就导致匿名函数使用的变量不同,结果也就是不再共享一个变量
    j定义在for外部,每次生成匿名函数使用的都是使用的同一个j
    (在for循环内部改变j的值不会影响该性质)
    j定义在for循环内部,每一次循环将产生一个新的j变量,三个匿名函数使用的也就不是同一个j了
  */
  fmt.Println(temp[0](), temp[0](), temp[0]())
  fmt.Println(temp[1](), temp[1](), temp[1]())
  fmt.Println(temp[2](), temp[2](), temp[2]())
}


总结


Go语言是一门面向过程编程语言,但是合理的使用函数也可以达到与面向对象编程语言类似的结果,Go语言函数灵活,操作也较为方便。

相关实践学习
日志服务之使用Nginx模式采集日志
本文介绍如何通过日志服务控制台创建Nginx模式的Logtail配置快速采集Nginx日志并进行多维度分析。
相关文章
|
22天前
|
存储 监控 算法
员工上网行为监控中的Go语言算法:布隆过滤器的应用
在信息化高速发展的时代,企业上网行为监管至关重要。布隆过滤器作为一种高效、节省空间的概率性数据结构,适用于大规模URL查询与匹配,是实现精准上网行为管理的理想选择。本文探讨了布隆过滤器的原理及其优缺点,并展示了如何使用Go语言实现该算法,以提升企业网络管理效率和安全性。尽管存在误报等局限性,但合理配置下,布隆过滤器为企业提供了经济有效的解决方案。
68 8
员工上网行为监控中的Go语言算法:布隆过滤器的应用
|
1月前
|
Go 开发工具
百炼-千问模型通过openai接口构建assistant 等 go语言
由于阿里百炼平台通义千问大模型没有完善的go语言兼容openapi示例,并且官方答复assistant是不兼容openapi sdk的。 实际使用中发现是能够支持的,所以自己写了一个demo test示例,给大家做一个参考。
|
1月前
|
存储 Go 索引
go语言中的数组(Array)
go语言中的数组(Array)
112 67
|
2天前
|
算法 安全 Go
Go语言中的加密和解密是如何实现的?
Go语言通过标准库中的`crypto`包提供丰富的加密和解密功能,包括对称加密(如AES)、非对称加密(如RSA、ECDSA)及散列函数(如SHA256)。`encoding/base64`包则用于Base64编码与解码。开发者可根据需求选择合适的算法和密钥,使用这些包进行加密操作。示例代码展示了如何使用`crypto/aes`包实现对称加密。加密和解密操作涉及敏感数据处理,需格外注意安全性。
27 14
|
2天前
|
Go 数据库
Go语言中的包(package)是如何组织的?
在Go语言中,包是代码组织和管理的基本单元,用于集合相关函数、类型和变量,便于复用和维护。包通过目录结构、文件命名、初始化函数(`init`)及导出规则来管理命名空间和依赖关系。合理的包组织能提高代码的可读性、可维护性和可复用性,减少耦合度。例如,`stringutils`包提供字符串处理函数,主程序导入使用这些函数,使代码结构清晰易懂。
30 11
|
2天前
|
存储 安全 Go
Go语言中的map数据结构是如何实现的?
Go 语言中的 `map` 是基于哈希表实现的键值对数据结构,支持快速查找、插入和删除操作。其原理涉及哈希函数、桶(Bucket)、动态扩容和哈希冲突处理等关键机制,平均时间复杂度为 O(1)。为了确保线程安全,Go 提供了 `sync.Map` 类型,通过分段锁实现并发访问的安全性。示例代码展示了如何使用自定义结构体和切片模拟 `map` 功能,以及如何使用 `sync.Map` 进行线程安全的操作。
|
7天前
|
监控 安全 算法
深度剖析核心科技:Go 语言赋能局域网管理监控软件进阶之旅
在局域网管理监控中,跳表作为一种高效的数据结构,能显著提升流量索引和查询效率。基于Go语言的跳表实现,通过随机化索引层生成、插入和搜索功能,在高并发场景下展现卓越性能。跳表将查询时间复杂度优化至O(log n),助力实时监控异常流量,保障网络安全与稳定。示例代码展示了其在实际应用中的精妙之处。
31 9
|
16天前
|
算法 安全 Go
Go 语言中实现 RSA 加解密、签名验证算法
随着互联网的发展,安全需求日益增长。非对称加密算法RSA成为密码学中的重要代表。本文介绍如何使用Go语言和[forgoer/openssl](https://github.com/forgoer/openssl)库简化RSA加解密操作,包括秘钥生成、加解密及签名验证。该库还支持AES、DES等常用算法,安装简便,代码示例清晰易懂。
51 12
|
19天前
|
监控 算法 安全
解锁企业计算机监控的关键:基于 Go 语言的精准洞察算法
企业计算机监控在数字化浪潮下至关重要,旨在保障信息资产安全与高效运营。利用Go语言的并发编程和系统交互能力,通过进程监控、网络行为分析及应用程序使用记录等手段,实时掌握计算机运行状态。具体实现包括获取进程信息、解析网络数据包、记录应用使用时长等,确保企业信息安全合规,提升工作效率。本文转载自:[VIPShare](https://www.vipshare.com)。
26 0
|
1月前
|
Go 数据安全/隐私保护 UED
优化Go语言中的网络连接:设置代理超时参数
优化Go语言中的网络连接:设置代理超时参数