网站名称大全,qingdao城乡住房建设厅网站,提供做网站服务好,wordpress使用jsonGo语言中的函数go语言中函数特性go语言有三种函数#xff1a;普通函数、匿名函数#xff08;没有名称的函数#xff09;方法#xff08;定义在struct上的函数#xff09;。receivergo语言中不运算函数重载#xff08;overload#xff09;#xff0c;也就是说不允许函数…Go语言中的函数go语言中函数特性go语言有三种函数普通函数、匿名函数没有名称的函数方法定义在struct上的函数。receivergo语言中不运算函数重载overload也就是说不允许函数同名go语言中的函数不能嵌套但是可以嵌套匿名函数函数是一个值可以将函数赋值给变量使得这个变量也成为函数函数可以作为参数传递给另一个函数函数的返回值可以是另一个函数函数调用的时候如果有参数传递给函数则先拷贝参数的副本再将副本传递给函数函数参数可以没有名称go语言中函数的定义和调用函数在使用之前必须先定义可以调用函数来完成某个任务函数可以重复调用从而达到代码的复用func function_name([parameter_list])[return_types]{函数体
}package mainimport fmtfunc sum(a int, b int) (res int) {res a breturn res
}
func main() {res : sum(1, 2)fmt.Printf(res: %v\n, res)
}
package mainimport fmtfunc compare(a int, b int) (max int) {if a b {max a} else {max b}return max
}
func main() {res : compare(1, 2)fmt.Printf(res: %v\n, res)
}go语言中的return没有返回值有一个返回值 例如上面的求和以及比较两个数的大小的函数存在多个返回值且在return中指定返回的内容多个返回值返回值名称没有被使用return覆盖命名返回值返回值名称没有被使用package mainimport fmtfunc test() {fmt.Print(testing...)
}
func main() {test()
}
package mainimport fmtfunc test() (string, int) {name : Y4y17age : 24return name, age
}
func main() {name, age : test()fmt.Printf(name: %v\n, name)fmt.Printf(age: %v\n, age)
}package mainimport fmtfunc test() (name string, age int) {name Y4y17age 24return //相当于return name,age
}
func main() {name, age : test()fmt.Printf(name: %v\n, name)fmt.Printf(age: %v\n, age)
}package mainimport fmtfunc test() (name string, age int) {n : Y4y17 //重新定义了n和a那么返回的时候只能返回n和a而不是name和agea : 24 //这种情况一般不这样写一般就是直接去掉返回值中的name和age只保留类型return n, a
}
func main() {name, age : test()fmt.Printf(name: %v\n, name)fmt.Printf(age: %v\n, age)
}Go中经常会使用其中一个返回值作为函数是否执行成功、是否有错误信息的判断条件例如return value,exists、return value,ok、return value,err等当函数的返回值过多的时候例如有4个以上的返回值应该将这些返回值收集到容器中然后以返回容器的方式去返回。例如同类型的返回值可以放进slice中不同类型的返回值可以放进map中。当函数有多个返回值的时候如果其中某个或者是某几个返回值不想用可以通过下划线_来丢弃这些返回值。函数的参数package mainimport fmtfunc test(a int) {a 200 //test函数中修改变量a的值为200
}
func main() {a : 5 //定义变量a的值为5test(a)fmt.Printf(a: %v\n, a)//输出a的值依然还是5
}数组、切片、指针都是传地址也就是传址的方式package mainimport fmtfunc test(s []int) {s[2] 17
}
func main() {s : []int{1, 2, 3, 4}test(s)fmt.Printf(s: %v\n, s)//输出的结果为s: [1 2 17 4]
}变长参数package mainimport fmt
//其实就像是传递了一个数组或者是切片
func test(args ...int) {for _, v : range args {fmt.Printf(v: %v\n, v)}
}
func main() {test(1, 2, 3, 4, 5, 6, 7)
}package mainimport fmtfunc test(name string, b bool, args ...int) {fmt.Printf(name: %v\n, name)fmt.Printf(b: %v\n, b)for _, v : range args {fmt.Printf(v: %v\n, v)}
}
func main() {test(Y4y17, true, 1, 2, 3, 4, 5, 6, 7)
}函数中的type关键字相当于在c语言中的typedef关键字说白了就是对现有的数据类型起了一个别名package mainimport fmtfunc add(a int, b int) int {return a b
}
func comp(a int, b int) int {if a b {return a} else {return b}
}
func main() {type f func(a int, b int) intff : addr : ff(1, 2)fmt.Printf(r: %v\n, r)ff compr ff(1, 2)fmt.Printf(r: %v\n, r)
}Go高阶函数函数作为参数package mainimport fmtfunc test(name string, f func(string)) { f(name)
}
func sayHello(name string) {fmt.Printf(Hello: %v\n, name)
}
func main() {test(Y4y17, sayHello)
}//test函数接受两个参数分别是string类型的name和func函数类型的f函数名sayHello函数接受一个参数即string类型的name主函数中调用test函数传递参数Y4y17,和sayHello函数名那么test函数中便会执行sayHello(Y4y17)函数作为返回值package mainimport fmtfunc add(a int, b int) int {return a b
}
func sub(a int, b int) int {return a - b
}
func test(operate string) func(int, int) int {//test函数接受一个string类型的参数operatetest函数返回值是一个函数该函数有两个int类型的参数并且返回值也是int类型switch operate {case ://当operate是的时候返回add方法return addcase -://当operate是-的时候返回sub方法return subdefault:return nil}
}func main() {f : test(-)res : f(1, 2)fmt.Printf(res: %v\n, res)
}匿名函数前面提到了在函数中是不允许嵌套函数的但是我们可以使用匿名函数来实现一些简单的功能package mainimport fmtfunc main() {//匿名函数和普通函数的区别其实就是没有了函数的名字当在一个函数中不写函数名的时候就是匿名函数max : func(a int, b int) int {if a b {return a} else {return b}}(1, 2) //直接在最后面加上()以及实参的时候就是自己调用自己//r : max(3, 8) //fmt.Printf(r: %v\n, r)fmt.Printf(max: %v\n, max)
}Golang闭包闭包可以理解成定义在一个函数内部的函数。在本质上闭包是将函数内部和函数外部连接起来的桥梁或者是说函数和其引用环境的组合体闭包指的是一个函数和与其相关的应用环境组合而成的实体。简单来说闭包函数引用环境。看下面的例子package mainimport fmt//定义一个函数名为test该函数返回值是一个函数这个函数有一个int类型的参数 并且他返回值是一个int类型的数
func test() func(int) int {var x intreturn func(i int) int {x ireturn x}
}
func main() {f : test()//f赋值为test的返回值就是返回的函数初始x为0fmt.Printf(f(10): %v\n, f(10)) //计算01010 这里x就变成了10 而不是0fmt.Printf(f(20): %v\n, f(20)) //计算102030 这里x就变成了30 而不是10fmt.Printf(f(30): %v\n, f(30)) //计算303060 这里x就变成了60 而不是30
}变量f是一个函数并且他引用了其外部作用域中的x变量此时f就是一个闭包。在f的生命周期内变量x也一直有效package mainimport (fmtstrings
)func makeSuffixFunc(suffic string) func(string) string {return func(name string) string {//这里的strings.HasSuff(name.suffic)表示判断name是否以suffic结尾//如果是返回true否则false 需要导包stringsif !strings.HasSuffix(name, suffic) {return name suffic} else {return name}}
}
func main() {f : makeSuffixFunc(World)str : f(Hello)fmt.Printf(str: %v\n, str)
}package mainimport fmtfunc cal(base int) (func(int) int, func(int) int) {add : func(a int) int {base areturn base}sub : func(a int) int {base - areturn base}return add, sub
}
func main() {add, sub : cal(10)res : add(10)fmt.Printf(res: %v\n, res)res sub(5)fmt.Printf(res: %v\n, res)
}定义了cal函数cal函数存在一个形参basecal函数返回值存在两个并且这两个都是函数之后在cal函数中定义两个匿名的函数分别赋值给add 和 sub最终cal函数返回这两个匿名函数之后在main函数中令add sub为cal(10) ,其中base就是10 之后执行resadd(10)而这个10是匿名函数的形参a10执行basea故base20base的值会存储下来之后res sub(5)此时sub函数中的形参a就是5再次执行base-a故得到base15Go语言中的递归函数函数内部调用函数自身的函数称之为递归函数使用递归函数最重要的三点递归就是自己调用自己必须先定义函数的退出条件没有退出条件递归将成为死循环go语言递归函数很可能会产生一大堆的goroutine也很可能会出现占空间内存溢出的问题package mainimport fmt//数的阶乘
func fc(n int) int {if n 1 {return 1} else {res : n * fc(n-1)return res}
}
func main() {res : fc(5)fmt.Printf(res: %v\n, res)
}package mainimport fmt
//f(n)f(n-1)f(n-2) f(2)f(1)1
func fb(n int) int {if n 2 {return 1} else {res : fb(n-1) fb(n-2)return res}
}
func main() {fmt.Printf(fb(3): %v\n, fb(3))
}Go语言中的defer语句go语言中的defer语句会将其后面跟随的语句进行延时处理在defer归属的函数即将返回时姜堰市处理的语句按defer定义的逆序进行执行也就是说先被defer的语句最后被执行最后被defer的语句最先被执行package mainimport fmtfunc main() {fmt.Printf(start...\n)defer fmt.Printf(stop1...\n)defer fmt.Printf(stop2...\n)defer fmt.Printf(stop3...\n)fmt.Printf(END...\n)
}输出结果如下Go语言中的init函数golang有一个特殊的函数init函数先于main函数的执行主要实现包级别的一些初始化操作init函数额主要特点init函数先于main函数自动执行不能被其他函数调用init函数没有输入参数、返回值每个包可以有多个init函数包的每个源文件也可以有多个init函数这点比较特殊同一个包的init执行顺序golang没有明确的定义不同包的init函数按照包导入的依赖关系决定执行顺序初始化顺序变量初始化init()main()package mainimport fmtvar i int initVar()func initVar() int {fmt.Printf(initvar...\n)return 100
}
func init() {fmt.Printf(init2...\n)
}
func init() {fmt.Printf(init...\n)
}
func main() {fmt.Printf(start...\n)
}输出结果为同时存在多个init()的时候遵循自上而下的执行顺序