(学go语言要多久)(学习go语言需要多久)

对每一个开发者来说,Go 的发展历史是必须知道的知识。了解几年来每个发行版本的主要变化,有助于理解 Go 的设计思想和每个版本的优势/弱点。

Go 1.0 — 2012 年 3 月:

Go 的第一个版本,带着一份兼容性说明文档来保证与未来发布版本的兼容性,进而不会破坏已有的程序。

第一个版本已经有 go tool pprof 命令和 go vet 命令。 go tool pprof 与 Google 的 pprof C++ profiler 稍微有些差异。go vet(前身是 go tool vet)命令可以检查包中潜在的错误。

垃圾回收:完全串行的标记和清除过程,需要暂停整个程序;

Go 1.1 — 2013 年 5 月:

这个 Go 版本专注于优化语言(编译器,gc,map,go 调度器)和提升它的性能。 这个版本也嵌入了竞争检测,在语言中是一个很强大的工具。 重写了 Go 调度器 显著地提升了性能。

垃圾回收:在多核主机并行执行垃圾收集的标记和清除阶段11;

Go 1.2 — 2013 年 12 月:

本版本中 test 命令支持测试代码覆盖范围并提供了一个新命令 go tool cover 。

Go 1.3 — 2014 年 6 月:

这个版本对栈管理做了重要的改进。栈可以申请连续的内存片段,提高了分配的效率,使下一个版本的栈空间降到 2KB。

栈频繁申请/释放栈片段会导致某些元素变慢,本版本也改进了一些由于上述场景糟糕的分配导致变慢的元素。

这个版本在 sync 包中发布了 Pool。 这个元素允许我们复用结构体,减少了申请的内存的次数,同时也是很多 Go 生态获得改进的根源,如标准库或包里的 encoding/json 或 net/http,还有 Go 社区里的 zap。

Go 团队也对通道作了改进,让它们变得更快。

垃圾回收:运行时基于只有指针类型的值包含指针的假设增加了对栈内存的精确扫描支持,实现了真正精确的垃圾收集

Go 1.4 — 2014 年 12 月:

此版本带来了官方对 Android 的支持,golang.org/x/mobile ) 让我们可以只用 Go 代码就能写出简单的 Android 程序。

归功于更高效的 gc,之前用 C 和汇编写的运行时代码被翻译成 Go 后,堆的大小降低了 10% 到 30%。

与版本无关的一个巧合是,Go 项目管理从 Mercurial 移植到了 Git,代码从 Google Code 移到了 Github。

Go 也提供了 go generate 命令通过扫描用 //go:generate 指示的代码来简化代码生成过程。

Go 1.5 — 2015 年 8 月:

这个新版本,发布时间推迟了两个月,目的是在以后每年八月和二月发布新版本:

这个版本对 gc 进行了重新设计。归功于并发的回收,在回收期间的等待时间大大减少。

这个版本也发布了运行时追踪,用命令 go tool trace 可以查看。

垃圾回收:实现了基于三色标记清扫的并发垃圾收集器13;大幅度降低垃圾收集的延迟从几百 ms 降低至 10ms 以下;计算垃圾收集启动的合适时间并通过并发加速垃圾收集的过程;

Go 1.6 — 2016 年 2 月:

这个版本最重大的变化是使用 HTTPS 时默认支持 HTTP/2。

在这个版本中 gc 等待时间也降低了:

垃圾回收:实现了去中心化的垃圾收集协调器;基于显式的状态机使得任意 Goroutine 都能触发垃圾收集的状态迁移;使用密集的位图替代空闲链表表示的堆内存,降低清除阶段的 CPU 占用14;

Go 1.7 — 2016 年 8 月:

这个版本发布了 context 包,为用户提供了处理超时和任务取消的方法。

对编译工具链也作了优化,编译速度更快,生成的二进制文件更小,有时甚至可以减小 20% 到 30%。

垃圾回收:通过并行栈收缩将垃圾收集的时间缩短至 2ms 以内15;

Go 1.8 — 2017 年 2 月:

把 gc 的停顿时间减少到了 1 毫秒以下。 其他的停顿时间已知,并会在下一个版本中降到 100 微秒以内。 这个版本也改进了 defer 函数。

垃圾回收:使用混合写屏障将垃圾收集的时间缩短至 0.5ms 以内16;

Go 1.9 — 2017 年 8 月:

这个版本增加了一些别名声明。 sync 包新增了一个 Map 类型,是并发写安全的。

垃圾回收:彻底移除暂停程序的重新扫描栈的过程17;

Go 1.10 — 2018 年 2 月:

test 包引进了一个新的智能 cache,运行会测试后会缓存测试结果。如果运行完一次后没有做任何修改,那么开发者就不需要重复运行测试,节省时间。

为了加快构建速度,go build 命令现在也维持了一份最近构建包的缓存。

这个版本没有对 gc 做实际的改变,但是确定了一个新的 SLO(Service-Level Objective)

垃圾回收:更新了垃圾收集调频器(Pacer)的实现,分离软硬堆大小的目标18;

Go 1.11 — 2018 年 8 月:

Go 1.11 带来了一个重要的新功能:Go modules。module机制的实验性引入,以试图解决长久以来困扰Gopher们的包依赖问题;

第二个特性是实验性的 WebAssembly,为开发者提供了把 Go 程序编译成一个可兼容四大主流 Web 浏览器的二进制格式的能力。这样以后Gopher们可以通过Go语言编写前端应用了。

Go 1.12 — 2019 年 2 月:

基于 analysis 包重写了 go vet 命令,为开发者写自己的检查器提供了更大的灵活性。

Go 发布的上一个版本中,对 Go module 的初步支持是默认关闭的,这暗示了它尚遗留着很多实现的问题。事实上,当时 replace 的支持连 module、package、import path 这三个最基本概念都是含混的。

而在 Go 1.12 中,这些问题都得到了解决,Go module 的正式发布又关闭了一条无脑喷 Go 的路径,真正的 Go 用户可以更安心方便地使用 Go。

Go 1.12 的 STW 停顿较 1.11 版本又有明显的缩短。

Go 1.12 的 trace 工具加入了 Minimum Mutator Utilization 图的支持,它可以极其方便地发现 GC 性能受限的情况。

Go 1.12 较为及时地提供了初步的 TLS 1.3 支持。

Timer 与 Deadline 的性能得到了优化,在 connection 上设置 deadline 的代价降低

默认启用 TCP KeepAlive

OS 包开始提供 UserHomeDir 函数,不再需要使用第三方库进行跨平台支持

在 macOS 上调用 File.Sync 并不能确保实际落盘的问题已解决

垃圾回收:使用新的标记终止算法简化垃圾收集器的几个阶段19;

Go 1.13 — 2019 年 9 月:

改进了 sync 包中的 Pool,在 gc 运行时不会清除 pool。它引进了一个缓存来清理两次 gc 运行时都没有被引用的 pool 中的实例。

重写了逃逸分析,减少了 Go 程序中堆上的内存申请的空间。

垃圾回收:通过新的 Scavenger 解决瞬时内存占用过高的应用程序向操作系统归还内存的问题20;

Go1.14 - 2020 年 2 月

现在 Go Module 已经可以用于生产环境,鼓励所有用户迁移到 Module。该版本支持嵌入具有重叠方法集的接口。性能方面做了较大的改进,包括:进一步提升 defer 性能、页分配器更高效,同时 timer 也更高效。

垃圾回收:使用全新的页分配器优化内存分配的速度21;

Go1.15 - 2020 年 8 月

Go 1.15版本不再对darwin/386和darwin/arm两个32位平台提供支持了。Go 1.15及以后版本仅对darwin/amd64和darwin/arm64版本提供支持。并且不再对macOS 10.12版本之前的版本提供支持。

Go 1.15 包括对链接器的实质性改进,改进了高核心数下小对象的分配,并弃用了X.509 CommonName。 GOPROXY现在支持跳过返回错误的代理,并添加了新的嵌入式 tzdata 包。

由于Go 1.15删除了一些GC元数据和一些无用的类型元数据,Go 1.15编译出的二进制文件size会减少5%左右。

Go1.16 - 2021 年 2 月

从这个版本起,环境变量 GO111MODULE 的默认值正式修改为 on。

Go1.16 起可以在 go.mod 文件中使用 retract 指令来声明该第三方模块的某些发行版本不能被其他模块使用。

Go 1.16新增go:embed指示符和embed标准库包,二者一起用于支持在在Go二进制文件中嵌入静态文件。

当GODEBUG环境变量包含inittrace=1时,Go运行时将会报告各个源代码文件中的init函数的执行时间和内存开辟消耗情况。

既Go 1.15实现了go linker的第一阶段优化后,Go 1.16中继续实施了对linker的第二阶段优化。优化后的链接器要平均比Go 1.15的快20%-25%,消耗的内存却减少5%-15%。

Go 1.17 新特性

时间:2021.08

官方说明:Go 1.17 Release Notes - The Go Programming Language

主要特性:

  • 从切片到数组指针的转换: []T 类型的表达式 s 现在可以转换为数组指针类型 *[N]T
  • go modules 支持“修剪模块图”(Pruned module graphs):go mod tidy -go=1.17
  • 编译器带来了额外的改进:即一种传递函数参数和结果的新方法,程序性能提高了约 5%,amd64 平台的二进制大小减少了约 2%。
  • unsafe包新增了unsafe.Add和unsafe.Slice
  • go.mod 中添加 // Deprecated: 注释来弃用模块
  • net包:
  • url参数解析增加对“;”的支持变化(原先 example?a=1;b=2&c=3 会解析成 map[a:[1] b:[2] c:[3]], 现在解析成map[c:[3]])
  • 增加 IP.IsPrivate 判断私有 IP
  • a.b.c.d 格式的 ip v4 地址不允许每段有前缀 0(因为某些系统会认为前缀 0 表示 8进制)

Go 1.18 新特性

时间:2022.03

官方说明:Go 1.18 Release Notes - The Go Programming Language

主要特性:

  • 泛型支持
  • Workspaces 工作区
  • Go编译器与Go module变化:修正的语法bug,在AMD64平台上引入architectural level,为ARM64架构带来高达 20% 的 CPU 性能改进:但由于编译器中与支持泛型有关的变化,Go 1.18 的编译速度可能比Go 1.17的编译速度大约慢15%。编译后的代码的执行时间不受影响。打算在Go 1.19中提高编译器的速度。Go 1.18明确了能修改go.mod、go.sum的命令只有三个:go get、go mod tidy和go mod download。
  • go fuzzing test:将fuzz testing纳入了go test工具链,与单元测试、性能基准测试等一起成为了Go原生测试工具链中的重要成员,单元测试函数名样式:FuzzXxx
  • go get 不再执行编译和安装工作
  • gofmt支持并发
  • 内置函数Append对切片的扩容算法发生变化:和Go 1.17以1024作为大小分界不同,Go 1.18使用256作为threshold
  • 新增net/netip包
  • tls client默认将使用TLS 1.2版本
  • crypto/x509包默认将拒绝使用SHA-1哈希函数签名的证书(自签发的除外)
  • strings包和bytes包新增Cut函数
  • runtime/pprof精确性提升
  • sync包新增Mutex.TryLock、RWMutex.TryLock和RWMutex.TryRLock

GO 1.19 新特性

时间:2022.05

官方说明:Go 1.19 Release Notes - The Go Programming Language

主要特性:

  • 泛型问题fix
  • 修订Go memory model:对Go memory model做了更正式的整体描述,增加了对multiword竞态、runtime.SetFinalizer、更多sync类型、atomic操作以及编译器优化方面的描述。
  • 修订go doc comment格式:增加了对超链、列表、标题、标准库API引用等格式支持
  • 新增runtime.SetMemoryLimit和GOMEMLIMIT环境变量:避免Go程序因分配heap过多,超出系统内存资源限制而被kill,默认memory limit是math.MaxInt64,limit限制的是go runtime掌控的内存总量,对于开发者自行从os申请的内存(比如通过mmap)则不予考虑。
  • 启动时将默认提高打开文件的限值:对于导入os包的go程序,Go将在1.19中默认提高这些限制值到hard limit。
  • race detector将升级到v3版thread sanitizer:race detector性能相对于上一版将提升1.5倍-2倍,内存开销减半,并且没有对goroutine的数量的上限限制
  • 增加"unix" build tag://go:build unix
  • 标准库net包使用EDNS
  • 标准库flag包增加TextVar函数
  • 正式支持64位龙芯cpu架构 (GOOS=linux, GOARCH=loong64)
  • 当Go程序空闲时,Go GC进入到周期性的GC循环的情况下(2分钟一次),Go运行时现在会在idle的操作系统线程上安排更少的GC worker goroutine,减少空闲时Go应用对os资源的占用。
  • Go行时将根据goroutine的历史平均栈使用率来分配初始goroutine栈,避免了一些goroutine的最多2倍的goroutine栈空间浪费。
  • sync/atomic包增加了新的高级原子类型Bool, Int32, Int64, Uint32, Uint64, Uintptr和Pointer,提升了使用体验。
  • Go编译器使用jump table重新实现了针对大整型数和string类型的switch语句,平均性能提升20%左右。

声明:我要去上班所有作品(图文、音视频)均由用户自行上传分享,仅供网友学习交流,版权归原作者kamactor所有,原文出处。若您的权利被侵害,请联系删除。

本文标题:(学go语言要多久)(学习go语言需要多久)
本文链接:https://www.51qsb.cn/article/m9hbq.html

(0)
打赏微信扫一扫微信扫一扫QQ扫一扫QQ扫一扫
上一篇2023-07-17
下一篇2023-07-17

你可能还想知道

发表回复

登录后才能评论