Go语言高效编程的3个技巧总结

 更新时间:2023年01月03日 15:19:19   作者:InterestingFigure  
Go语言是一种开源编程语言,可轻松构建简单、可靠且高效的软件,下面这篇文章主要给大家分享介绍了关于Go语言高效编程的3个技巧,文中通过实例代码介绍的非常详细,需要的朋友可以参考下

不要使用Logrus

这其实和泛型有关。因为Go语言是一门强类型的静态语言,所以你不可能像NodeJS或者PHP那样绕过数据类型。那如果我们还需要使用通用的类型怎么办呢?比如像Loger,或者ORM,因为只有使用了通用的类型,才能编写出通用的代码,不然每个都要写一次。

最终,我们只能用反射。而 Logrus 大量使用反射,这导致大量分配计数。虽然通常不是一个大问题(取决于代码),但性能很重要,尤其是在大规模、高并发的项目中。虽然这听起来像是一个非常小的优化,但避免反射很重要。如果你看到一些可以不考虑类型而使用结构的代码,它会使用反射并且会对性能产生影响。

例如,Logrus 并不关心类型,但显然 Go 需要知道(最终)。Logrus 怎么办呢?使用反射来检测类型,这是开销。

log.WithFields(log.Fields{<!--{C}%3C!%2D%2D%20%2D%2D%3E-->
“animal”: myWhatever,
}).Info(“A walrus appears”)

所以我会更喜欢zerolog,当然zap也不错。两者都宣称零分配,这也是我们希望的,因为它们的性能影响最小。

不要使用encoding/json

当我们需要一个功能、函数的时候,很多人都建议使用标准库。但是标准库中的encoding/json模块是个例外。其实也和上面的例子一样,encoding/json使用反射,这会导致性能不高,并且在编写返回 json 响应的 API 、或者微服务时会造成损失。

比如你可以使用 Easyjson,它很简单,也很高效,它是使用代码生成器来创建将结构转换为 json 所需的代码,以最大限度地减少分配。这是一个手动构建步骤,很烦人。有趣的是json-iterator也使用反射,但速度明显更快,我怀疑是黑魔法。

尽可能不要在goroutine中使用闭包

比如,下面这个示例代码:

for i:=0;i<10;i++ {
  go func() {
     fmt.Println(i)
  }()
}

大多数人可能期望这会打印数字 0 到 9,就像将任务委托给 goroutine 时那样。

但是实际结果:根据系统,你将得到一两个数字和许多 10。

为什么会这样?闭包可以访问父作用域,因此可以直接使用变量。尽管更新的 linters 可能会警告你“变量闭包捕获”,但并不会要求你重新声明该变量。

Go 的性能名声很大程度上归功于执行的运行时优化,它尝试“猜测”你想要做什么并优化某些执行路径。在此期间,它“捕获”变量并以理论上最有效的方式将它们传递到需要它们的地方(例如,在完成一些非并发操作以释放某些 CPU 上的分配之后)。这种情况下的结果是循环可能会启动 goroutines,goroutines可能会在很晚之后从父作用域接收到 i 的值。不能保证在多次执行此代码时你会看到哪个,可能是数字10,也可以是其他数字。

如果你出于某种原因确实使用了闭包,一定要传递变量i,就像对待每个函数一样对待闭包。

总结

到此这篇关于Go语言高效编程的3个技巧总结的文章就介绍到这了,更多相关Go语言高效编程内容请搜索脚本之家以前的文章或继续浏览下面的相关文章希望大家以后多多支持脚本之家!

相关文章

  • Go语言七篇入门教程二程序结构与数据类型

    Go语言七篇入门教程二程序结构与数据类型

    这篇文章主要为大家介绍了Go语言的程序结构与数据类型,本篇文章是Go语言七篇入门系列文,有需要的朋友可以借鉴参考下,希望能够有所帮助
    2021-11-11
  • Go json反序列化“null“的问题解决

    Go json反序列化“null“的问题解决

    本文主要介绍了Go json反序列化“null“的问题解决,文中通过示例代码介绍的非常详细,对大家的学习或者工作具有一定的参考学习价值,需要的朋友们下面随着小编来一起学习学习吧
    2023-03-03
  • Go语言使用protojson库实现Protocol Buffers与JSON转换

    Go语言使用protojson库实现Protocol Buffers与JSON转换

    本文主要介绍Google开源的工具库Protojson库如何Protocol Buffers与JSON进行转换,以及和标准库encoding/json的性能对比,需要的朋友可以参考下
    2023-09-09
  • 浅析Golang中的协程(goroutine)

    浅析Golang中的协程(goroutine)

    在Go语言中,协程(goroutine)是轻量级的线程,它是Go语言中实现并发编程的基础,Go语言中的协程是由Go运行时调度器(scheduler)进行管理和调度的,本文将给大家简单的介绍一下Golang中的协程,需要的朋友可以参考下
    2023-05-05
  • Goland 2020或2019软件版本去掉a...或fmt...提示的方法

    Goland 2020或2019软件版本去掉a...或fmt...提示的方法

    这篇文章主要介绍了Goland 2020或2019软件版本去掉a...或fmt...提示的方法,本文通过图文并茂的形式给大家介绍的非常详细,对大家的学习或工作具有一定的参考借鉴价值,需要的朋友可以参考下
    2020-10-10
  • 使用Go语言解析动态JSON格式的方法

    使用Go语言解析动态JSON格式的方法

    本篇文章主要介绍了使用Go语言解析动态JSON格式的方法,小编觉得挺不错的,现在分享给大家,也给大家做个参考。一起跟随小编过来看看吧
    2017-12-12
  • Go 标准库增加metrics指标探讨分析

    Go 标准库增加metrics指标探讨分析

    go中有一个神奇的标准库 runtime/metrics,提供了一系列预定义好的 Go 自身的相关指标,如果没有编写过基础监控库或者关注的比较少的朋友可能会没接触到这类指标,本文展开现有metrics 指标,并结合现有的社区讨论一起看看还有没有必要增加更多的标准库指标
    2023-10-10
  • Golang中处理import自定义包出错问题的解决办法

    Golang中处理import自定义包出错问题的解决办法

    最近开始使用Go/GoLand在import自定义包时出现各种状况,下面这篇文章主要给大家介绍了关于Golang中处理import自定义包出错问题的解决办法,文中通过图文介绍的非常详细,需要的朋友可以参考下
    2023-11-11
  • 详解如何使用Golang实现自定义规则引擎

    详解如何使用Golang实现自定义规则引擎

    规则引擎的功能可以简化为当满足一些条件时触发一些操作,通常使用 DSL 自定义语法来表述,本文给大家介绍了如何使用Golang实现自定义规则引擎,文中有相关的代码示例供大家参考,需要的朋友可以参考下
    2024-05-05
  • Golang实现文件传输功能

    Golang实现文件传输功能

    这篇文章主要为大家详细介绍了Golang实现文件传输功能,文中示例代码介绍的非常详细,具有一定的参考价值,感兴趣的小伙伴们可以参考一下
    2022-07-07

最新评论