内容简介:用函数实现接口,这样在调用的时候就会非常简便,这一类型的函数就叫做接口型函数;上面案例,我们定义了仅有一个函数签名Done (k , v interface{}) 的Handle类型接口,接着我们定义一个each函数,接收两个参数:一个map、一个Handle类型,之后遍历map, 调用Handle约束函数Done,操作map的key 和value。现在我们已经定义好接口类型约束,接着我们要去使用了,请看如下使用案例:仔细想想,以上使用案例有两个有两个缺陷:
Golang过程式编程
1、接口型函数
用函数实现接口,这样在调用的时候就会非常简便,这一类型的函数就叫做接口型函数; 使用情景 :仅限于只有一个函数签名的接口。
-
原始使用,请看如下使用案例:
type Handle interface { Done (k , v interface{}) } func each(m map[interface{}]interface{}, h Handle) { if m != nil && len(m) > 0 { for k, v := range m { h.Done(k, v) } } }
上面案例,我们定义了仅有一个函数签名Done (k , v interface{}) 的Handle类型接口,接着我们定义一个each函数,接收两个参数:一个map、一个Handle类型,之后遍历map, 调用Handle约束函数Done,操作map的key 和value。现在我们已经定义好接口类型约束,接着我们要去使用了,请看如下使用案例:
type student struct {} func (self *student) Done(k, v interface{}) { fmt.Printf("student's name is: %s, age is: %d \n", k, v) } func main(){ m := make(map[interface{}]interface{}) m["sampsom"] = 25 m["jiny"] = 30 each(m, &student{}) }
仔细想想,以上使用案例有两个有两个缺陷:
a、因为接口只是一个约定的规则,不能直接使用,因此我们必须定义一个类型来实现这个接口,才能使用Handle约束的函数Done
b、既然是实现Handle类型接口,所以必须遵循Handle类型的约束规则,必须实现接口约束的方法Done。我们就不能够随心所欲的定义自己想要定义的更有意义的方法签名
既然原始的接口使用方式,有上面的两个缺陷,那么我们想要在约定的规则里,怎么才能随心所欲的玩了,这就要我们的 接口型函数 来救场了
-
接口型函数的使用,请看如下案例:
type Handle interface { Done (k , v interface{}) } type HandleFunc func(f , v interface{}) func (f HandleFunc) Done(k , v interface{}) { h(k, v) }
请看上面案例,因为HandleFunc类型,是一个和Handle接口类型约束的方法Done签名一样的函数类型,因此我们可以把Done方法的调用以HandleFunc函数调用来替换。现在只要是和HandleFunc也即是和Done一样签名的函数,就可以使用HandleFunc(yourFunc),来强制转换我们自己定义的更有意义的函数为HandleFunc类型函数,从而持有Done方法,而调用自己了。请看下面我们如何来使用:
func echoString(k , v interface{}) { fmt.Printf("student's name is: %s, age is: %d \n", k, v) } func main(){ m := make(map[interface{}]interface{}) m["sampsom"] = 25 m["jiny"] = 30 each(m, HandleFunc(echoString)) }
现在我们的实现方式是不是更简单了,只要依据HandleFunc类型的签名方式定义好我们自己想要定义的函数,就可以直接使用了,而不用再去定义类型来实现Handle接口了,不过人都是爱偷懒的,每次调用时都要这样HandleFunc(echoString)强制转化,有没有更好的方式了,请看下面我们的完整案例:
package main
import "fmt" type Handle interface { Done (k , v interface{}) } func each(m map[interface{}]interface{}, h Handle) { if m != nil && len(m) > 0 { for k, v := range m { h.Done(k, v) } } } //each函数包装优化 func EachFunc(m map[interface{}]interface{}, f func(k , v interface{})) { each(m, HandleFunc(f)) } //接口型函数实现 type HandleFunc func(k , v interface{}) func (h HandleFunc) Done(k , v interface{}) { h(k, v) } func echoString(k , v interface{}) { fmt.Printf("student's name is: %s, age is: %d \n", k, v) } //原始实现 type student struct {} func (self *student) Done(k, v interface{}) { fmt.Printf("student's name is: %s, age is: %d \n", k, v) } func main(){ m := make(map[interface{}]interface{}) m["sampsom"] = 25 m["jiny"] = 30 EachFunc(m, echoString) }
2、middleware 中间件
3、validator 请求校验
4、golang如何实现插件化编程
5、闭包
6、递归函数
7、运行时候选择函数
7.1 使用映射和函数引用来制造分支
7.1 动态的创建函数
8、泛型函数
9、高阶函数
10、纯记忆函数
以上所述就是小编给大家介绍的《八、Golang过程式编程》,希望对大家有所帮助,如果大家有任何疑问请给我留言,小编会及时回复大家的。在此也非常感谢大家对 码农网 的支持!
猜你喜欢:- Go语言开发-过程式编程-类型断言
- Go语言开发-过程式编程-IF语句
- Go语言开发-过程式编程-For循环语句
- Go语言开发-过程式编程-通信和并发语句
- Go语言开发-过程式编程-switch语句-类型开关
- Go语言开发-过程式编程-Panic和Recover
本站部分资源来源于网络,本站转载出于传递更多信息之目的,版权归原作者或者来源机构所有,如转载稿涉及版权问题,请联系我们。