首页 > 其他分享 >【4.0】Go语言语法基础之函数

【4.0】Go语言语法基础之函数

时间:2023-11-11 11:15:36浏览次数:34  
标签:foo 4.0 int 语法 func Go 返回值 main 函数

【一】函数基础

【1】语法

func关键字 函数名(形参1 形参1的类型,形参2 形参2的类型) (返回值类型) {
    函数体(函数体的内容和缩进无关,只要是在大括号内,都是函数体内容)
}
  • 在Python中需要先定义函数再使用
  • 在Go中不需要先定义再使用
func main() {

}

【2】无参数无返回值

package main

import "fmt"

func main() {
	// (2)在main函数中调用 index 函数
	index() // 这是index函数
}

// (1)简单的函数定义 :无参数 , 无返回值
// 定义函数后在main函数中调用
func index() {
	fmt.Println("这是index函数")
}

【3】有参数无返回值

  • 有参数无返回值,且参数类型不同
package main

import "fmt"

func main() {
	// (2)在main函数中调用 index 函数 需要传递两个参数,并且 参数要符合规定
	// 只有位置传参,没有所谓的关键字传参
	index("Dream", 18) // Dream 18
}

// (1)有参数无返回值的函数
// 定义函数后在main函数中调用
func index(name string, age int) {
	fmt.Println(name, age)
}
  • 有参数无返回值,且参数类型相同
package main

import "fmt"

func main() {
    // (2)在main函数中调用 index 函数 需要传递两个参数,并且 参数要符合规定
    // 只有位置传参,没有所谓的关键字传参
    index(19, 18) // 
}

// (1)有参数无返回值的函数
// 定义函数后在main函数中调用
// name 和 age 都是相同类型 可简写
func index(name, age int) {
    fmt.Println(name, age)
}
  • 有参数无返回值,且参数类型不同
package main

import "fmt"

func main() {
    // (2)在main函数中调用 index 函数 需要传递两个参数,并且 参数要符合规定
    // 只有位置传参,没有所谓的关键字传参
    index(19, 18, "dream","hope") 
}

// (1)有参数无返回值的函数
// 定义函数后在main函数中调用 name 和 age 都是数字类型 , gender 和 class 都是字符串类型
func index(name, age int,gender,class string) {
    fmt.Println(name, age,gender,class)
}

【4】2个参数和1个返回值

package main

import "fmt"

func main() {
	// (2)在main函数中调用 index 函数 需要传递两个参数,并且 参数要符合规定
	// 只有位置传参,没有所谓的关键字传参
	// 调用返回值需要先定义接收返回值的变量名
	res := index("Dream", 18)
	fmt.Println(res)
	// Dream 18
	// 18
}

// (1)两个参数和一个返回值
// 定义函数后在main函数中调用
func index(name string, age int) int {
	fmt.Println(name, age)

	// 返回值需要定义返回值类型,否则会报错
	// return age // Too many arguments to return
	return age // Too many arguments to return

}

【5】2个参数和2个返回值

package main

import "fmt"

func main() {
	// (2)在main函数中调用 index 函数 需要传递两个参数,并且 参数要符合规定
	// 只有位置传参,没有所谓的关键字传参
	// 调用返回值需要先定义接收返回值的变量名
	res, result := index("Dream", 18)
	fmt.Println(res, result)
	// Dream 18
	// Dream 18
}

// (1)两个参数和两个返回值 --- 多个返回值需要加 ()
// 定义函数后在main函数中调用
func index(name string, age int) (string, int) {
	fmt.Println(name, age)

	// 返回值需要定义返回值类型,否则会报错
	// return age // Too many arguments to return
	return name, age // Too many arguments to return
}

【6】_代替不需要接收的返回值

package main

import "fmt"

func main() {
	// (3)在main函数中调用 index 函数 需要传递两个参数,并且 参数要符合规定
	// 只有位置传参,没有所谓的关键字传参
	// 调用返回值需要先定义接收返回值的变量名 , 可以用 _ 代替不要的返回值
	//a, b, c := index(6, 18)
	//fmt.Println(a, b, c) // 6 18 108
	_, _, c := index(6, 18)
	fmt.Println(c) // 108

}

// (1)两个参数和两个返回值 --- 多个返回值需要加 ()
// 定义函数后在main函数中调用
func index(a, b int) (int, int, int) {

	// 返回值需要定义返回值类型,否则会报错
	return a, b, a * b
}

【7】命名返回值

package main

import "fmt"

func main() {
	// (4)在main函数中调用 index 函数 需要传递两个参数,并且 参数要符合规定
	// 只有位置传参,没有所谓的关键字传参
	// 调用返回值需要先定义接收返回值的变量名 , 可以用 _ 代替不要的返回值
	// 命名返回值的使用
	add, mul := index(6, 18)
	fmt.Println(add, mul) // 24 108
}

// (1)两个参数和两个返回值 --- 多个返回值需要加 ()
// 定义函数后在main函数中调用
func index(a, b int) (add int, mul int) {
	// [1] add / mul : 相当于定义了两个返回值的变量名,在函数内部不用定义就可以直接使用
	// 命名返回值
	// 返回值需要定义返回值类型,否则会报错
	//return a + b, a * b
	add = a + b
	mul = a * b

	// [2] return 可以直接省略掉 return add , mul
	return
}

【二】函数高级

【1】不定长参数

package main

import "fmt"

// 补充 : 同一个包下,不能出现同名的变量和变量名 (py以py文件为最小单位,go以包为最小单位)
func main() {
	// 调用函数 : [1 2 3 4] 容器类型
	// Python 有可变长位置参数 和 可变长关键字参数 , 但是 go 只有 可变长位置参数
	foo(1, 2, 3, 4) // [1 2 3 4]
}

// 不定长参数
// 可以接收任意长度的数字类型的参数 : ...interface
func foo(a ...int) {
	fmt.Println(a)
}

【2】匿名函数

(1)基本的匿名函数

package main

import (
	"fmt"
)

// 补充 : 同一个包下,不能出现同名的变量和变量名 (py以py文件为最小单位,go以包为最小单位)
func main() {
	// 调用函数 : [1 2 3 4] 容器类型
	// Python 有可变长位置参数 和 可变长关键字参数 , 但是 go 只有 可变长位置参数
	foo()
	// 这是 foo 函数内部
	//这是 foo 函数内部的匿名函数
}

// 匿名函数 --- 没有名字的函数 (需要定义在函数内部)

func foo(a ...int) {

	fmt.Println("这是 foo 函数内部")
	// 匿名函数 : 定义在函数内部的函数 , 必须是匿名函数
	func() {
		fmt.Println("这是 foo 函数内部的匿名函数")
	}() // 匿名函数要加 () 调用执行
}

(2)有参数的匿名函数

package main

import (
	"fmt"
)

// 补充 : 同一个包下,不能出现同名的变量和变量名 (py以py文件为最小单位,go以包为最小单位)
func main() {
	// 调用函数 : [1 2 3 4] 容器类型
	// Python 有可变长位置参数 和 可变长关键字参数 , 但是 go 只有 可变长位置参数
	foo()
	// 这是 foo 函数内部
	//这是 foo 函数内部的匿名函数
}

// 匿名函数 --- 没有名字的函数 (需要定义在函数内部)

func foo(a ...int) {

	fmt.Println("这是 foo 函数内部")
	// 匿名函数 : 定义在函数内部的函数 , 必须是匿名函数
	// 有参数的匿名函数
	// 位置参数 a,b 均为 int 类型
	func(a, b int) {
		fmt.Println("这是 foo 函数内部的匿名函数")
	}(4, 5) // 匿名函数要加 () 调用执行,未知参数必须传入参数才不会报错
}

(3)有参数并且有返回值的匿名函数

package main

import (
	"fmt"
)

// 补充 : 同一个包下,不能出现同名的变量和变量名 (py以py文件为最小单位,go以包为最小单位)
func main() {
	// 调用函数 : [1 2 3 4] 容器类型
	// Python 有可变长位置参数 和 可变长关键字参数 , 但是 go 只有 可变长位置参数
	foo()
	// 这是 foo 函数内部
	//这是 foo 函数内部的匿名函数
}

// 匿名函数 --- 没有名字的函数 (需要定义在函数内部)

func foo(a ...int) {

	fmt.Println("这是 foo 函数内部")
	// 匿名函数 : 定义在函数内部的函数 , 必须是匿名函数
	// 有参数的匿名函数
	// 位置参数 a,b 均为 int 类型
	// 有参数,有返回值的匿名函数
	res := func(a, b int) int {
		fmt.Println("这是 foo 函数内部的匿名函数")
		return a * b
	}(4, 5) // 匿名函数要加 () 调用执行,未知参数必须传入参数才不会报错

	fmt.Println("这是 匿名函数的返回值 :>>>> ", res)
}

【3】函数是一等公民

package main

import "fmt"

// 补充 : 同一个包下,不能出现同名的变量和变量名 (py以py文件为最小单位,go以包为最小单位)
func main() {
	// 调用函数
	foo()
}

// 匿名函数也是一种类型 ---> 函数是一等公民 ---> 头等函数
func foo() {
	// 一门语言,只要函数是一等公民的意思是可以把函数当成变量来使用,传递

	// 函数是一等公民 ---> 可以把函数赋值给一个变量
	var f = func() {
		fmt.Println("我是 foo 函数内部的匿名函数")
	}
	// 调用函数
	f() // 我是 foo 函数内部的匿名函数
	// 查看函数的类型
	fmt.Printf("匿名函数的类型是 :>>>> %T", f) // 匿名函数的类型是 :>>>> func()

	// 既然函数是变量,就可以当参数传递,也可以当返回值返回
}
package main

import "fmt"

// 补充 : 同一个包下,不能出现同名的变量和变量名 (py以py文件为最小单位,go以包为最小单位)
func main() {
	// 调用函数
	foo()
}

// 匿名函数也是一种类型 ---> 函数是一等公民 ---> 头等函数
func foo() {
	// 一门语言,只要函数是一等公民的意思是可以把函数当成变量来使用,传递

	// 函数是一等公民 ---> 可以把函数赋值给一个变量 -- 完整定义
	var f func() = func() {
		fmt.Println("我是 foo 函数内部的匿名函数")
	}
	// 调用函数
	f() // 我是 foo 函数内部的匿名函数
	// 查看函数的类型
	fmt.Printf("匿名函数的类型是 :>>>> %T", f) // 匿名函数的类型是 :>>>> func()

	// 既然函数是变量,就可以当参数传递,也可以当返回值返回
}

【4】闭包函数

(1)引入

package main

import "fmt"

// 补充 : 同一个包下,不能出现同名的变量和变量名 (py以py文件为最小单位,go以包为最小单位)
func main() {
	// 调用函数
	foo()
}

// 闭包函数 : 必须符合两个 条件
// 1 :定义在函数内部
// 2 :对外部作用域有引用
func foo() func() {
	f := func() { // 这样写只满足了第一个条件 :定义在函数内部 , 所以不是闭包函数
		fmt.Println("我是 foo 函数内部的匿名函数")
	}
	return f
}

(2)闭包函数

  • Go 有闭包函数,但是没有装饰器的语法糖
package main

import "fmt"

// 补充 : 同一个包下,不能出现同名的变量和变量名 (py以py文件为最小单位,go以包为最小单位)
func main() {
	// 调用函数
	f := foo()
	f()
	// 这是foo函数的结果调用  Dream
	// 我是 foo 函数内部的匿名函数
	// 这是foo函数 内部的匿名函数的结果调用  Dream
}

// 闭包函数 : 必须符合两个 条件
// 1 :定义在函数内部
// 2 :对外部作用域有引用
func foo() func() {
	name := "Dream"
	f := func() { // 【1】定义在函数内部,
		fmt.Println("我是 foo 函数内部的匿名函数")
		// 【2】并对外部作用域有引用
		fmt.Println("这是foo函数 内部的匿名函数的结果调用 ", name)
	}
	fmt.Println("这是foo函数的结果调用 ", name)
	return f
}

【5】函数的参数和返回值都是类型的一部分

(1)函数的参数是类型的一部分

package main

import "fmt"

// 补充 : 同一个包下,不能出现同名的变量和变量名 (py以py文件为最小单位,go以包为最小单位)
func main() {
	// 调用函数
	f := foo()
	f(4, 5) // 我是 foo 函数内部的匿名函数  20
}

// 函数是一种类型,函数的参数和返回值都是类型的一部分
func foo() func(a, b int) {
	return func(a, b int) { 
		fmt.Println("我是 foo 函数内部的匿名函数 ", a*b)
	}
}

(2)函数的返回值是类型的一部分

package main

import "fmt"

// 补充 : 同一个包下,不能出现同名的变量和变量名 (py以py文件为最小单位,go以包为最小单位)
func main() {
	// 调用函数
	f := foo()
	f() 
}

// 函数是一种类型,函数的参数和返回值都是类型的一部分
// func(a, b int) int  外层定义函数的参数类型及返回值类型
func foo() func(a, b int) int {
	// func(a, b int) int  内层定义 函数的参数类型及 内部函数的返回值类型
	return func(a, b int) int {
		fmt.Println("我是 foo 函数内部的匿名函数 ", a*b)
		return a * b
	}
}

(3)函数也可以作为参数

package main

import "fmt"

// 补充 : 同一个包下,不能出现同名的变量和变量名 (py以py文件为最小单位,go以包为最小单位)
func main() {
	// 调用函数
	f := foo()
	f() 
}

// 函数是一种类型,函数的参数和返回值都是类型的一部分
// func(a int, b func()) int  外层定义函数的参数类型(a 为int,b 为一个函数)及返回值类型(返回了一个数字所以是 int)
func foo() func(a int, b func()) int {
	// func(a, b int) int  内层定义 函数的参数类型 (a 为int,b 为一个函数)及 内部函数的返回值类型(返回了一个数字所以是 int)
	return func(a int, b func()) int {
		fmt.Println("我是 foo 函数内部的匿名函数 ")
		return a
	}
}

【6】给类型重命名

package main

import "fmt"

// 补充 : 同一个包下,不能出现同名的变量和变量名 (py以py文件为最小单位,go以包为最小单位)
func main() {
	// 调用函数
	f := foo()
	f(4, 5) // 我是 foo 函数内部的匿名函数  20
}

// 给类型重命名
type Myfunc func(a int, b func()) int

// 函数是一种类型,函数的参数和返回值都是类型的一部分
// func(a int, b func()) int  外层定义函数的参数类型(a 为int,b 为一个函数)及返回值类型(返回了一个数字所以是 int)
func foo() Myfunc {
	// func(a, b int) int  内层定义 函数的参数类型 (a 为int,b 为一个函数)及 内部函数的返回值类型(返回了一个数字所以是 int)
	return func(a int, b func()) int {
		fmt.Println("我是 foo 函数内部的匿名函数 ")
		return a
	}
}

标签:foo,4.0,int,语法,func,Go,返回值,main,函数
From: https://www.cnblogs.com/dream-ze/p/17825655.html

相关文章

  • 【3.0】Go语言语法初识之变量
    【零】注释语法注释就是对代码的解释和说明,其目的就是让人们更加轻松的了解代码。注释是开发人员的一个重要的习惯。单行注释使用//开头多行注释使用/*开头*/结尾//package定义包名main包名packagemain//import引用库fmt库名import"fmt"//func定......
  • Shell中的for与while循环结构语法
    1for循环语法结构如下:for变量名in值1值2值3        #值的数量决定循环任务的次数do命令序列done1.1for循环的基本语法格式#编写脚本,进行测试[root@localhostopt]#vimfor01.sh#!/bin/bashforiinabcdoecho"helloworld"done[root@loca......
  • C语言入门:基本语法
    如果你刚刚接触到C语言,而且感到自己写不出代码,别灰心,这是正常的学习过程。学习编程是一个渐进的过程,不要急于求成。通过不断的实践和学习,你会发现编程变得越来越容易。当你刚开始学习C语言时,最好从一个简单的"Hello,World!"程序开始,这是学习任何编程语言的传统入门方式。以下是一......
  • go.mod file not found in current directory or any parent directory; see 'go help
    go.modfilenotfoundincurrentdirectoryoranyparentdirectory;see'gohelpmodules'(exitstatus1)原因:目录少缺少 go.mod文件。解决方法:在终端中输入:gomodinitmain 其中main是模块名。 ......
  • GoKIT v2.1是一种基于云的物联网开发平台,旨在帮助开发者快速构建物联网应用程序。
    GoKITv2.1是一种基于云的物联网开发平台,旨在帮助开发者快速构建物联网应用程序。它提供了一组简单易用的工具和API,使开发者能够轻松地与各种类型的设备和传感器进行交互,并实时处理数据。GoKITv2.1的主要特点包括:设备管理:可以轻松管理连接到平台的设备,包括添加、删除和重新配置设......
  • Ubuntu14.04 Server 升级到14.10 的方法
    如果想从Ubuntu14.04/13.10/13.04/12.10/12.04或者更老的版本升级到14.10,只要遵循下面给出的步骤。注意,你不能直接从13.10升级到14.10。你应该先将13.10升级到14.04在从14.04升级到14.10。下面是详细步骤。下面的步骤不仅能用于14.10,也兼容于一些像Lubuntu14.10,Kubuntu14.10和Xu......
  • Go中字符串处理:fmt.Sprintf与string.Builder的比较
    在Go语言中,我们通常会遇到两种主要的方式来处理和操作字符串:使用fmt.Sprintf函数和string.Builder类型。尽管两者都可以实现字符串的格式化和连接,但它们在性能和用法上有一些关键区别。1.fmt.Sprintffmt.Sprintf是一个函数,它根据提供的格式化字符串和参数列表,将它们格式化为一......
  • godot常用C#代码
    Godot常用C#代码注:本文记录的是我个人认为很常用但是容易忘记的C#代码。生成实例:生成实例的对象必须是PackedScene类型生成实例如果想用其它类型存储需要强制转换,即在变量名前括号加变量名,或用az强转代码示例:usingGodot;usingSystem;publicpartialclassworl......
  • The governance measures of marine oil pollution
    Thegovernancemeasures(1).Preventivemeasures.Preventionisoneofthemosteffectivecontrolmethods,includingthefollowingaspects:a.Strengtheningmonitorandcontrolsystem,improvingthesoundmonitoringsystem,andestabilishingthe real-time......
  • webgoat _v8.1全流程通关
    1.1(A1)SQLInjection(intro)概念 本课程介绍了什么是结构化查询语言(SQL),以及如何操纵它以执行开发人员原始意图之外的任务。 目标 用户将对SQL的工作原理和用途有基本的了解。 用户将对SQL注入有基本的了解,以及它们的工作原理。 用户将展示对以下内容的知识: ......