这是我参与「第五届青训营 」笔记创作活动的第4天
本堂课重点内容
- 如何编写高质量代码
- 如何评价Go语言程序性能
- 如何避免常见性能陷阱
详细知识点介绍
代码是写给人看的,需要保证代码的可读性。
可以使用gofmt来进行统一的代码格式化。
注释应该解释代码作用/如何做的/这样做的原因/什么情况会出错。
公共符号必须有注释。
变量离其被使用的地方越远,变量名需要越详细。如循环变量可以只用i,全局变量需要包含很多上下文信息。
控制流程应避免嵌套。如使用return直接跳出嵌套所有的if,结束函数。
应保证正常代码路径为最小缩进,即能够连续地看完。
Go语言自带benchmark性能测试工具。可使用go test -bench命令。
要提升slice和map的性能,最好在声明变量的时候就为其分配空间,避免之后扩容对性能造成影响。
在一个底层数组基础上创建的slice,只要有一个未被释放,整个底层数组就得不到释放。因此在大slice上创建小slice可以使用copy进行复制,避免小slice让原底层数组得不到释放。
在拼接字符串时,应避免使用加号进行拼接,而应使用strings.Builder或bytes.Buffer进行拼接。因为直接使用加号进行拼接的话,会重新分配一块内存给新的字符串,这就产生了额外的开销。后二者底层是基于[]byte的,不会有那么多重新分配内存的过程。二者相比,strings.Builder要稍快一点,因为bytes.Buffer在最后转换成string时需要重新分配内存,strings.Builder直接返回[]byte的起始地址。
在go中可以定义不占内存的空结构体。可以将空结构体作为map的value,这样一来,map便可当做其他语言的set使用,只关心key是否存在。空结构体的技巧也可以用于给interface{}占位,如果你并不需要传数据给该接口的话。
简单的原子操作可以使用atomic库来实现,该库使用硬件操作来实现原子性的。而锁是使用操作系统提供的系统调用,性能不如atomic。