降低代码的圈复杂度——复杂代码的解决之道 (3)

从一个对象列表中获取一个ID列表

如果在go中,我们可以这么做。

go实现

略显繁琐,熟悉Java的同学可能会说,这么简单的功能为什么会写的这么复杂,于是三下五除二写下了如下的代码。

使用linq重构前

上图中使用了Java8的新特性Stream,而Go语言目前还无法达到这样的效果。于是就该轮到go-linq出场了,使用go-linq之后的代码就变成了如下的模样。

使用go-linq重构后

怎么样,是不是看到Java 8 Stream的影子,重构之后的代码我们暂且不去比较行数,从语意上看,同样的清晰直观,这就是go-linq,我们用了一个例子来为大家介绍了它的定义,接下来简单介绍几种常见的用法,这些都是官网上给的例子。

4.1 ForEach

与Java 8中的foreach是类似的,就是对集合的一个遍历。

image-20201229093033157

首先是一个From,这代表了输入,梦开始的地方,可以和Java 8中的stream划等号。

然后可以看到有ForEach和ForEachT,ForEachIndexed和ForEachIndexedT。前者是只遍历元素,后者则将其下标也一起打印了出来。跟Go中的Range是一样的,跟Java 8的ForEach也类似,但是Java 8的ForEach没有下标,之所以go-ling有,是因为它自己记录了一个index,ForEachIndexed源码如下。

ForEachIndexed源码

其中两者的区别是啥呢?我认识是你对你要遍历的元素的类型是否敏感,其实大多数情况应该都是敏感的。如果你使用了带T的,那么在遍历的时候go-ling会将interface转成你在函数中所定义的类型,例如fruit string。

否则的话,就需要我们自己去手动的将interface转换成对应的类型,所以后续的所有的例子我都会直接使用ForEachT这种类型的函数。

4.2 Where

可以理解为SQL中的where条件,也可以理解为Java 8中的filter,按照某些条件对集合进行过滤。

where用法

上面的Where筛选出了字符串长度大于6的元素,可以看到其中有个ToSlice,就是将筛选后的结果输出到指定的slice中。

4.3 Distinct

与你所了解到的MySQL中的Distinct,又或者是Java 8中的Distinct是一样的作用,去重

4.3.1 简单场景

distinct去重

4.3.2 复杂场景

当然,实际的开发中,这种只有一个整形数组的情况是很少的,大部分需要判断的对象都是一个struct数组。所以我们再来看一个稍微复杂一点的例子。

复杂对象的distinct

上面的代码是对一个products的slice,根据product的Code字段来进行去重。

4.4 Except

对两个集合做差集。

4.4.1 简单场景

except简单场景

4.4.2 复杂场景

except-复杂场景

4.5 Intersect

对两个集合求交集

4.5.1 简单场景

intersect简单场景

4.5.2 复杂场景

intersect复杂场景

4.6 Select

从功能上来看,Select跟ForEach是差不多的,区别如下。

Select 返回了一个Query对象

内容版权声明:除非注明,否则皆为本站原创文章。

转载注明出处:https://www.heiqu.com/wssxyw.html