go 语言变量作用域及闭包

Go 语言变量作用域

作用域为已声明标识符所表示的常量、类型、变量、函数或包在源代码中的作用范围。

Go 语言中变量可以在三个地方声明

函数内定义的变量称为 局部变量
函数外定义的变量称为 全局变量
函数定义中的变量称为 形式参数

局部变量

在函数体内声明的变量称之为局部变量,它们的作用域只在函数体内。

全局变量

在函数体外声明的变量称之为全局变量,全局变量可以在整个包甚至外部包(被导出后)使用,全局变量可以在任何函数中使用。

形式参数

形式参数会作为函数的局部变量来使用,作用域为函数内部。示例 :

package main

// 全局变量
var c int = 10

func test(i int) {
	// d 为局部变量
	// i 为形式参数
	// 作用范围为本行内部
	var d int = i
	println(d)
}

func main() {
	// d为局部变量此处无法打印
	// println(d)
	println(c)
}

go 语言闭包

1. 闭包是指有权访问另一个函数作用域中的变量的函数。

2. 创建闭包的常见方式就是在一个函数内部创建另一个函数, 内函数可以访问外函数的变量。

注意:闭包里作用域返回的局部变量不会被立刻销毁回收,但过度使用闭包可能会占用更多内存,导致性能下降。

示例 :

package main
import "fmt"

func getSequence() func() int {
	i := 0
	return func() int {
		i += 1
		return i
	}
}

func main() {
	/* nextNumber 为一个函数,函数 i 为 0 */
	nextNumber := getSequence()

	/* 调用 nextNumber 函数,i 变量自增 1 并返回 */
	fmt.Println(nextNumber())
	fmt.Println(nextNumber())
	fmt.Println(nextNumber())

	/* 创建新的函数 nextNumber1,并查看结果 */
	nextNumber1 := getSequence()
	fmt.Println(nextNumber1())
	fmt.Println(nextNumber1())
}