GO 1.18 新特性 (二):泛型 | 云端技能包

2022年4月20日 387点热度 0人点赞 0条评论

近日,Go 团队官宣 Go 1.18 正式发布!新版本有何值得关注的特性?快跟随汇量科技 Mobvista 技术 VP 兼首席工程架构师蔡超,一起感受全新升级的 Go——


文/汇量科技技术 VP 兼首席工程架构师 蔡超


上一期中,我们了解了Go 1.18 特性(一):模糊测试(Fuzzing Test),本期内容中,我将为大家介绍第二个特性——泛型

基本语法


定义可接受类型列表(constraint)

简单来说,Go 的泛型就是将参数类型定义为一个可接受类型的列表(称为constraint)。


直接上例子

例1: 方法定义上使用泛型

图片


例2: 结构类型定义上使用泛型

图片


以上例子中使用了一个预置的 constraint “any”,这里 any 就相当于 interface{},表示任何类型。


另一个预置的 constraint 是 comparable,代表可以支持==和!=比较的类型。

让列表更简单

用 “~”简化衍生类型的声明

上面型函数只能接受 constraint 列表中的类型作为调用的参数,包括这些类型的别名。但对于列表中类型的衍生类型就不能接受了。


例如:

图片


编译以上程序会引发编译错误,在 Go 中为了简化扩展类型的定义,我们可以通过"~"来表示支持类型扩展类型。利用这种方式修改方法定义即可修复上面的编译问题。

图片

定义 constraint 类型

虽然有了上面的对于扩展类型的简化定义方式,但还是会很容易产生很长的 contraint 类型列表,而且这个列表往往会需要在很多方法定义中重复。


为了简化和复用复杂的类型列表(constraint)声明,在 Go1.18 中可以通过 interface 来定义一个 constraint 类型。


1. interface 中定义 constraint 类型支持的方法


这种方式下方法所接受的类型必须要实现了该接口定义,即实现了该接口中包含的方法。

图片


这里你可能会有一个问题:既然使用了 interface,那完全可以使用多态--以接口 Addable 作为方法的参数,定义如下:

图片


问题来了:这里的 AddPoly 和上面使用泛型定义的 AddGen 一样吗?


答案是不一样的。


AddGen  的传入参数(a,b) 必须是同一类型,而不仅仅是都实现了 Addable 接口,上列中要么都是 type1,要么都是 type2。


而 AddPoly 方法就不同了,传入参数只要是实现了 Addable 就可以,即(a,b) 可以一个是 type1,另一个是 type2。


2. interface 中直接包含可接受类型列表


这里就比较直接,可以在一个 interface 中定义可接受类型的列表

图片


这个 constraint interface 可以在不同的地方被复用,Google 在"golang.org/x/exp/constraints"包中也贴心地提供了很多常用的 constraint interface。

关于性能

Go 的泛型实现影响性能吗?这是很多程序员最关心的问题。我们直接通过 Benchmark 程序来看结果。


1. constraint 为基础计算类型

图片


图片


可以看到, Go 泛型对于基本类型的影响几乎没有。


2. constraint 为接口定义的类型(这里指类型需要实现接口中的方法)

图片


图片


这种情况下泛型的性能明显要差于原有的多态实现。所以,类似情况最好不要使用泛型来替代多态,不仅没有简化程序,反而对性能有一定影响。

写给 Java 程序员:

关于类型擦除

Java 程序员都知道,Java 的泛型实现是编译时期的,在运行时是被擦除的,例如:

图片


由于类型擦除的缘故,li.getClass() == lf.getClass() 的结果是 true。


而 Go 的泛型则不是通过这种方式实现的,Go 采用了一种不完全的单态化(monomorphization) 被称为“GCShape stenciling with Dictionaries” 。这种实现方式也导致了我们在前面看到的性能测试的结果,具体细节,我将在未来的文章中和大家讨论。


图片

由于没有类型擦除,reflect.TypeOf(li) == reflect.TypeOf(lf)结果返回为 false。

以上为该特性的简单介绍。如需了解更多细节,可参考官方文档进行学习。

关注蔡超谈软件,了解更多内容?

————————————

不想再错过你的云端干货?点击“阅读原文”,或关注“云上说禅”吧!

相关阅读


图片


关于云上说禅

· 云上说禅作为Mobvista汇量科技云计算品牌官方账号,致力于为技术人打造云计算知识分享平台,并为用云企业提供深度行业洞察。
· 在这里,你将看到:


- 最实用的云计算知识科普及实践教学

- 最具洞见的行业趋势解读

- 最新鲜的产品动态

- 最有趣的技术人日常

73120GO 1.18 新特性 (二):泛型 | 云端技能包

这个人很懒,什么都没留下

文章评论