go从0到1项目实战体系四:函数

1. 函数:

. 声明:
   func 函数名字 (参数列表) (返回值列表){
   }. 举例:
   func add() {
   }
   func add(a int , b int) int {
   }
   func add(a int , b int) (int, int) {
   }. 特点:
   a. 不支持重载,一个包不能有两个名字一样的函数.
   b. 函数也是一种类型,一个函数可以赋值给变量(这个变量是一个指针指向函数地址).
   c. 匿名函数
   d. 多返回值
   e. type定义新的类型:type addFunc func(int, int) int  => 表示函数也是一种类型

④. 函数参数传递方式:
   a. 值传递
   b. 引用传递
   c. 值传递、引用传递,传递给函数的都是变量的副本.值传递是值的拷贝,引用传递是地址(8个字节)的拷贝.
   d. 一般来说,地址拷贝更为高效.值拷贝取决于拷贝的对象大小,对象越大,则性能越低.
   e. map、slice、chan、指针、interface默认以引用的方式传递.. 命名返回值的名字:
   func calc(a, b int) (sum int, avg int) {
   
      sum = a + b
      avg = (a +b) / 2
      return
   }. _标识符,用来忽略返回值.
   a, _ = add()
   _, a = add(). 可变参数:
   func add(arg…int) int {
   }              // 0个或多个参数
   func add(a int, arg…int) int {
   }       // 1个或多个参数,a是固定参数(可以有多个固定参数)
   a. arg是一个slice(切片).
   b. 通过arg[index]依次访问所有参数.
   c. 通过len(arg)来判断传递参数的个数.

2 defer:

(1). 概念:

. 当函数返回时,执行defer语句.因此,可以用来做资源清理.. 多个defer语句,按先进后出的方式执行(最晚的先执行).. defer语句中的变量,defer声明时就决定了.. 举例:
   var a int = 111
   defer fmt.Println(a)      // 第3执行,打印值为111.在defer定义时,是什么值就是什么值.跟后面没关系.
   defer fmt.Println("333")  // 第2执行,因为先进后出,先入栈后出.
   a = 222
   fmt.Println(a)            // 第1执行
   结果:
   222
   333
   111

(2). 用途:

. 关闭文件句柄:
   file := open(filename)
   defer file.Close()
   // 文件操作. 锁资源释放:
   mc.Lock()
   defer mc.Unlock()
   // 其他操作. 数据库连接释放:
   conn := openDatabase()
   defer conn.Close()
   // 其他操作

3. 内置函数:

①. close:
   主要用来关闭channel.

②. len:
   用来求长度,如string、array、slice、map、channel.

③. new:
   用来分配内存(值类型),如int、struct.返回的是指针.
   a := new(int)         // 返回一个内存地址
   *a = 100

④. make:
   用来分配内存(引用类型),如chan、map、slice.

⑤. append:
   用来追加元素到数组、slice中.

⑥. panic和recover:
   用来做错误处理.
   defer func() {
      if err := recover(); err != nil {
         fmt.Println(err)
      }
   }()            // 匿名函数自调用

   func initConfig() (err error) {
      return errors.New("init config failed")
   }
   func main() {
      err := initConfig()
      if err != nil {
         panic(err)
      }
   }

3.1 new与make的区别:

. new:
   a. new一个[]int的切片                 => 第一行
   b. new返回一个指向切片的指针(*[]int)  => 第二行
   c. 这个地址指向一个实际的切片         => 第三行

②. make返回不是一个指针,就是一个切片.. 举例:
   c := new([]int)
	fmt.Println(c)             // &[],返回指向切片的指针.
	d := make([]int, 3)
	fmt.Println(d)             // [0 0 0],返回一个切片
   // 如果没有这句会报错:panic: runtime error: index out of range.
   // 因为new的时候,指针指向一个空的slice,slice没有初始化.
   *c = make([]int, 5)
   (*c)[0] = 1                // 因为是指针,加*号
	d[0] = 2

4. 递归函数:

斐波那契数(前两个数相加等于后一个数):

func fab(n int) int {
   
	if n <= 1 {
   
		return 1
	}
	return fab(n-1) + fab(n-2)
}
func main() {
   
	for i := 0; i < 10; i++ {
   
		n := fab(i)
		fmt.Println(n)
	}
}

5. 闭包:

一个函数和与其相关的引用环境组合而成的实体.

func Adder() func(int) int {
             // 返回一个函数func(int) int
   var x int
   return func(d int) int {
              // 这里必须与定义的返回函数一致
      x += d
      return x
   } 
}
func main() {
   
   var f = Adder()
   fmt.Print(f(1), " - ")             // 1
   fmt.Print(f(20), " - ")            // 21
   fmt.Print(f(300))                  // 321
}

相关推荐

  1. go01项目实战体系函数

    2023-12-22 14:06:04       45 阅读
  2. go01项目实战体系十:go包管理

    2023-12-22 14:06:04       40 阅读
  3. go01项目实战体系二十三:GORM

    2023-12-22 14:06:04       22 阅读
  4. golang01实战系统十:处理表单的输入

    2023-12-22 14:06:04       21 阅读
  5. 01实现YOLOv3

    2023-12-22 14:06:04       7 阅读

最近更新

  1. TCP协议是安全的吗?

    2023-12-22 14:06:04       16 阅读
  2. 阿里云服务器执行yum,一直下载docker-ce-stable失败

    2023-12-22 14:06:04       16 阅读
  3. 【Python教程】压缩PDF文件大小

    2023-12-22 14:06:04       15 阅读
  4. 通过文章id递归查询所有评论(xml)

    2023-12-22 14:06:04       18 阅读

热门阅读

  1. datacomp_large数据集下载,snapshot_download使用示例

    2023-12-22 14:06:04       41 阅读
  2. 面试手写代码总结

    2023-12-22 14:06:04       28 阅读
  3. 9月9日算法学习(队列)

    2023-12-22 14:06:04       39 阅读
  4. leetCode算法—13. 罗马数字转整数

    2023-12-22 14:06:04       41 阅读
  5. 创酷rs2022车机安装app

    2023-12-22 14:06:04       166 阅读
  6. 用过都说好用的API接口汇总,含免费次数

    2023-12-22 14:06:04       43 阅读
  7. P2437 蜜蜂路线

    2023-12-22 14:06:04       44 阅读