Go 语言笔试面试题(基础语法)
Q1 =
和 :=
的区别?
Q2 指针的作用?
答案
Q3 Go 允许多个返回值吗?
答案
Q4 Go 有异常类型吗?
答案
Q5 什么是协程(Goroutine)
答案
Goroutine 是与其他函数或方法同时运行的函数或方法。 Goroutines 可以被认为是轻量级的线程。 与线程相比,创建 Goroutine 的开销很小。 Go应用程序同时运行数千个 Goroutine 是非常常见的做法。
Q6 如何高效地拼接字符串
答案
Q7 什么是 rune 类型
答案
ASCII 码只需要 7 bit 就可以完整地表示,但只能表示英文字母在内的128个字符,为了表示世界上大部分的文字系统,发明了 Unicode, 它是ASCII的超集,包含世界上书写系统中存在的所有字符,并为每个代码分配一个标准编号(称为Unicode CodePoint),在 Go 语言中称之为 rune,是 int32 类型的别名。
Go 语言中,字符串的底层表示是 byte (8 bit) 序列,而非 rune (32 bit) 序列。例如下面的例子中 语
和 言
使用 UTF-8 编码后各占 3 个 byte,因此 len("Go语言")
等于 8,当然我们也可以将字符串转换为 rune 序列。
Q8 如何判断 map 中是否包含某个 key ?
答案
Q9 Go 支持默认参数或可选参数吗?
答案
Go 语言不支持可选参数(python 支持),也不支持方法重载(java支持)。
Q10 defer 的执行顺序
答案
- 多个 defer 语句,遵从后进先出(Last In First Out,LIFO)的原则,最后声明的 defer 语句,最先得到执行。
- defer 在 return 语句之后执行,但在函数退出之前,defer 可以修改返回值。
例如:
这个例子中,可以看到 defer 的执行顺序:后进先出。但是返回值并没有被修改,这是由于 Go 的返回机制决定的,执行 return 语句后,Go 会创建一个临时变量保存返回值,因此,defer 语句修改了局部变量 i,并没有修改返回值。那如果是有名的返回值呢?
这个例子中,返回值被修改了。对于有名返回值的函数,执行 return 语句时,并不会再创建临时变量保存,因此,defer 语句修改了 i,即对返回值产生了影响。
Q11 如何交换 2 个变量的值?
Q12 Go 语言 tag 的用处?
答案
tag 可以理解为 struct 字段的注解,可以用来定义字段的一个或多个属性。框架/工具可以通过反射获取到某个字段定义的属性,采取相应的处理方式。tag 丰富了代码的语义,增强了灵活性。
例如:
这个例子使用 tag 定义了结构体字段与 json 字段的转换关系,Name -> stu_name
, ID -> stu_id
,忽略 Age 字段。很方便地实现了 Go 结构体与不同规范的 json 文本之间的转换。
Q13 如何判断 2 个字符串切片(slice) 是相等的?
答案
go 语言中可以使用反射 reflect.DeepEqual(a, b)
判断 a、b 两个切片是否相等,但是通常不推荐这么做,使用反射非常影响性能。
通常采用的方式如下,遍历比较切片中的每一个元素(注意处理越界的情况)。
Q14 字符串打印时,%v
和 %+v
的区别
答案
Q15 Go 语言中如何表示枚举值(enums)
答案
Q16 空 struct{} 的用途
答案
使用空结构体 struct{} 可以节省内存,一般作为占位符使用,表明这里并不需要一个值。
|
|
比如使用 map 表示集合时,只关注 key,value 可以使用 struct{} 作为占位符。如果使用其他类型作为占位符,例如 int,bool,不仅浪费了内存,而且容易引起歧义。
再比如,使用信道(channel)控制并发时,我们只是需要一个信号,但并不需要传递值,这个时候,也可以使用 struct{} 代替。
再比如,声明只包含方法的结构体。