1.本发明涉及go语言技术领域,具体涉及一种基于go语言反射的类型转换方法及系统。


背景技术:

2.在使用go语言编写代码的时候,会遇到这样的一些问题。在go原生的sdk中,数据之间传输的时候需要用到序列化和反序列化,序列化和反序列化就是将一个对象数据转换到另一个服务的对象数据的应用层的实现流程,而这种转换流程本身是没有啥问题的,但是在真正的工程化实践里面,会遇到各种各样的格式化转换问题,这里将所有问题列举下:
3.第一:是强类型格式的转换问题,比如一方是uint8,另一方只关心结构不关心字段,按照int8来取数据就获取不到,这种情况就需要业务自己处理,要么早期开发阶段时候约定好接口字段类型,要么就自己改,自己改的话,在对接其他三方的接口时候,工作量很有可能会非常大,还有很多隐患,接口类型的不统一,以及不兼容。
4.第二:不支持自定义类型的格式转换,在go里面支持自定义类型转换,比如自定义一个别名类型叫mytype,这个mytype是unit8的别名,如果使用mytype来接收,则接收失败。在一些业务场景中自定义类型的格式也是使用比较频繁的一种方式,这种不支持的话,就需要业务自己做很多额外的处理。
5.第三:在工程中,很多时候项目是有多种语言编写而成的,而不同的语言他们对数据的大小写是有不同的语义的,这些在go项目中有点不一样,数据的首字母大小写在go语言的语法层面上有不同的意义,大写表示公共范围,外部都可以访问,消息是私有范围,只能文件内部进行访问。在go项目中如果要将对象序列化,如果不对属性做额外的处理,则最后输出的序列化后的数据是大写开头的。大写开头的数据,在其他工程上面要做兼容才行,否则识别不了。为了解决这个问题,go语言中的序列化框架json支持标签’json’,只需要在属性后面写上对外输出的字段即可,一般都是将属性开头小写的名字作为这里的处理。在工程中,需要对外和对内的一般都是接口,而接口字段数据量也真的是不小,这种在go工程代码中会形成非常多的冗余代码,非常难看。


技术实现要素:

6.针对现有技术的不足,本发明公开了一种基于go语言反射的类型转换方法及系统,用于解决在使用go语言编写代码的时候,会遇到的强类型格式的转换问题、不支持自定义类型的格式转换、编码规范问题。
7.本发明通过以下技术方案予以实现:
8.第一方面,本发明提供了一种基于go语言反射的类型转换方法,包括以下步骤:
9.将字符串通过json转换成map或者数组结构;
10.将对应的map或者数组作为第一个入参,待转换的对象的指针作为第二个参数;
11.使用map类型结构的api进行转换,对数组使用array结构的转换api继续转换。
12.更进一步的,所述方法中,api的入参是两个函数,第一个函数是字符串类型,第二个参数是要转换为的对象的指针。
13.更进一步的,所述方法中,map类型转map类型时,具体如下:
14.首先进行循环迭代,原map结构中的数据,其中的key对应的值转换到目标map结构中的key的结构对应的值;
15.进行value转换,如果目标map的value结构为struct,则原目标map的value结构为map或者struct;
16.对属性和对应的值进行循环迭代,然后再将原map的value中的属性的值转换为待要设置的目标的map的value的属性的值。
17.更进一步的,所述方法中,map结构转struct结构时,具体如下:
18.将map的值先转换为go中的value结构的类型,其中,value结构是golang语言中的反射时候使用的中间结构;
19.接收map的value的value结构后,进行向目标struct对应属性的类型进行转换;
20.进行转换类型的判断,然后根据目标类型进行不同类型的转换。
21.更进一步的,所述方法中,转换类型包括目标是struct结构类型、目标是map结构类型、目标是array或者slice结构类型、目标是基本类型。
22.更进一步的,所述方法中,struct结构转换struct结构时,具体如下:
23.获取属性对应的value之后,再向目标struct相同key对应的value进行转换,进行向目标struct对应属性的类型进行转换;
24.进行转换类型的判断,然后根据目标类型进行不同类型的转换。
25.更进一步的,所述方法中,struct结构转换map结构时,具体如下:
26.循环检索struct结构中的属性和属性对应的值,对于目标值,先创建一个map结构,然后直接将属性对应的值直接作为对应的value。
27.更进一步的,所述方法中,struct结构转换基本类型、struct结构转换slice或者array类型时直接报错。
28.更进一步的,所述方法中,slice或者array结构转换slice或者array结构时,数据结构对数组本身进行循环,然后将数组中的对象进行循环,挨个向目标结构进行转换输出结果。
29.第二方面,本发明提供了一种基于go语言反射的类型转换系统,包括处理器、存储器以及存储在所述存储器中且被配置为由所述处理器执行的计算机程序,所述存储器与所述处理器耦接,且所述处理器执行所述计算机程序时,实现第一方面所述的基于go语言反射的类型转换方法步骤。
30.本发明的有益效果为:
31.本发明实现弱类型的转换,只要是兼容的就可以转换,还有就是自定义的类型也可以兼容,无需额外添加标签进行标识就可以直接转换,在多语言的兼容中非常方便。
附图说明
32.为了更清楚地说明本发明实施例或现有技术中的技术方案,下面将对实施例或现有技术描述中所需要使用的附图作简单地介绍,显而易见地,下面描述中的附图仅仅是本
发明的一些实施例,对于本领域普通技术人员来讲,在不付出创造性劳动的前提下,还可以根据这些附图获得其他的附图。
33.图1是基于go语言反射的类型转换方法的原理框图。
具体实施方式
34.为使本发明实施例的目的、技术方案和优点更加清楚,下面将结合本发明实施例中的附图,对本发明实施例中的技术方案进行清楚、完整地描述,显然,所描述的实施例是本发明一部分实施例,而不是全部的实施例。基于本发明中的实施例,本领域普通技术人员在没有做出创造性劳动前提下所获得的所有其他实施例,都属于本发明保护的范围。
35.实施例1
36.本实施例提供了一种基于go语言反射的类型转换方法,包括以下步骤:
37.将字符串通过json转换成map或者数组结构;
38.将对应的map或者数组作为第一个入参,待转换的对象的指针作为第二个参数;
39.使用map类型结构的api进行转换,对数组使用array结构的转换api继续转换。
40.本实施例为了能够将一个类型转换到另外一个类型,而且另外一个类型的属性是能够接收到即可,因此这里根据原类型中的结构划分了不同的api。
41.本实施例中,在go语言中类型有多种,其中基本类型的转换不数据本工具的处理范畴,在框架的另外一些模块中有,这里处理的是非基本类型,而非基本类型,在go语言中有这么几种:字符串类型、map类型、struct结构、array结构、slice结构及reader对象。
42.本实施例出现reader对象,是因为实际项目中有用到该对象,该对象读取得到json字符串,因此这里对这部分进行了简单封装。
43.以下对上面的每一种类型转换做说明,首先我们需要说明的是,上面的每一种类型最后的转化结果是为了得到一种结构,这种结构是方便我们使用的结构体或者数组,而不是基本类型。
44.实施例2
45.在具体实施层面,本实施例对实施例1中的每一种类型转换做说明,首先我们需要说明的是,上面的每一种类型最后的转化结果是为了得到一种结构,这种结构是方便我们使用的结构体或者数组,而不是基本类型。
46.本实施例进行map类型转换map类型时,map类型转换到最后的结构,要么是结构体要么是另外一个map,不过结构是对应的key的首字母是小写,这就是我们要的结果。
47.本实施例主要流程有两个,一个是目标结构为map结构,一个是目标结构为struct结构。
48.本实施例中,目标结构也为map的结构,首先进行循环迭代,原map结构中的数据,其中的key对应的值转换到目标map结构中的key的结构对应的值。
49.本实施例value也要进行转换,value又可以分为各种各样的结构,即原map的value的结构和目标map的value的结构。
50.本实施例中,如果目标map的value结构为struct,那么原目标map的value结构为map或者struct均可,对其属性和对应的值进行循环迭代,然后再将原map的value中的属性的值转换为待要设置的目标的map的value的属性的值。
51.本实施例中,转换又是一层嵌套结构的转换,里面又是根据value对应的结构进行对应的转换。
52.本实施例转换后,就将转换后的值直接反射塞进对应目标map的value的值里面。
53.本实施例进行map结构转换struct结构时,目标结构是struct的结构,对于struct,我们就是进行map向struct结构的转换,这个转换第一步,会将map的值先转换为go中的value结构的类型,这个value结构是golang语言中的反射时候使用的中间结构。
54.本实施例对于拿到map的value的value结构后,需要进行向目标struct对应属性的类型进行转换。
55.本实施例转换有类型的判断:目标是struct结构类型、目标是map结构类型、目标是array或者slice结构类型、目标是基本类型(int、int8、int16、int32、int64、uint、uint8、uint16、uint32、uint64、float32、float64、bool、string),然后根据目标类型进行不同类型的转换。
56.本实施例中,如果目标类型为struct结构,则原类型需要为map类型或者struct类型,于是就有这样的转换:map类型——》struct结构和struct类型——》struct类型,其中map类型向struct结构转换上面有,下面介绍struct类型——》struct类型转换。
57.本实施例进行struct结构转换struct结构时,相同类型的转换,这个转换与map到struct的转换区别不大,不过获取属性对应的value方式有点区别,获取之后再向目标struct相同key对应的value进行转换,这个转换就又回到上面的向对应类型转换的方式了,具体的转换根据具体的类型转化即可。
58.本实施例中,目前是map结构的,则有如下两个:map结构——》map结构和struct结构——》map结构,其中map——》map结构,上面已经有说明,这里说明struct结构向map结构的转换。
59.本实施例进行struct结构转换map结构时,循环检索struct结构中的属性和属性对应的值,对于目标值,我们先创建一个map结构,然后直接将属性对应的值直接作为对应的value。
60.本实施例进行struct结构转换基本类型,这种是不支持的,直接会报错。同时struct结构转换slice或者array类型,这种类型也不支持。
61.本实施例进行slice或者array结构转换slice或者array结构时,对于数据结构对数组本身进行循环,然后将数组中的对象进行循环,挨个向目标结构进行转换,具体的转换,见上面的结构转换。
62.实施例3
63.本实施例提供一种基于go语言反射的类型转换系统,包括处理器、存储器以及存储在所述存储器中且被配置为由所述处理器执行的计算机程序,所述存储器与所述处理器耦接,且所述处理器执行所述计算机程序时,实现基于go语言反射的类型转换方法步骤。
64.综上,本发明实现弱类型的转换,只要是兼容的就可以转换,还有就是自定义的类型也可以兼容,无需额外添加标签进行标识就可以直接转换,在多语言的兼容中非常方便。
65.以上实施例仅用以说明本发明的技术方案,而非对其限制;尽管参照前述实施例对本发明进行了详细的说明,本领域的普通技术人员应当理解:其依然可以对前述各实施例所记载的技术方案进行修改,或者对其中部分技术特征进行等同替换;而这些修改或者
替换,并不使相应技术方案的本质脱离本发明各实施例技术方案的精神和范围。