# 更多关于Go的知识

《Go语言101》中的系列文章主要着墨于Go语法和语义。 更多和Go相关的话题并没有在《Go语言101》中详尽解释。 本文将对这些话题做一个简单的介绍，并提供一些链接供读者自行探索。

### 程序性能分析、基准测试、单元测试和模糊测试

我们可以使用Go官方工具链中的`go test`命令来运行单元测试和基准测试。 测试源文件名必须以`_test.go`结尾。 Go官方工具链也支持程序性能分析。 请阅读下列文章获取详情：

- Go程序性能分析
- `testing`标准库包
- 使用例子程序做测试.
- 使用子单元测试和子基准测试
- `go test`命令选项
- Go Fuzzing.

### gccgo

gccgo是Go核心团队维护开发的另一款Go编译器。 它的主要目的是为了验证标准编译器（gc）的正确性。 我们可以在`go run`、`go build`和`go install`等命令中使用选项`-compiler=gccgo`来指定使用gccgo编译器。 此选项需要安装`gccgo`软件包才能起作用。 gccgo命令也可单独运行。

### `go/*`标准库包

`go/*`标准库包提供Go源文件解析相关的功能。这些库包对于开发各种Go源代码分析工具很有帮助。 请阅读Go代码分析和这些库包的文档来获取如何使用这些库包中提供的功能。

### 系统调用

我们可以使用`syscall`标准库包中的函数来进行系统调用。 注意此标准库包和其它标准库包不同，它其中的函数是和具体操作系统相关的。

### Go汇编

Go函数可以使用Go汇编语言来编写。Go汇编是一种跨平台（尽管并非100%）的汇编语言。 Go汇编汇编常用来实现一些对性能要求很高的函数。

更多详情，请阅读下列文章：

- Go汇编快速导读
- Go汇编的设计

### cgo

通过cgo机制，我们可以在Go代码中调用C代码，或者反之。 请阅读下列链接获取详情：

- cgo官方文档
- C? Go? Cgo!
- Go维基中的cgo页面

通过C代码做为桥梁，我们也可以使C++和Go代码能够相互调用。

注意，cgo的使用将给跨平台Go项目的维护开发带来一些麻烦。另外Go和C之间互调不如Go-Go和C-C调用高效。

### 跨平台编译

标准Go编译器支持跨平台编译。通过设置`GOOS`和`GOARCH`两个环境变量，我们可以使用`go build`命令在Linux系统中编译出Windows和Mac程序，反之亦然。 请阅读下面的代码获取详情：

- 在Linux上编译Windows程序
- 目前支持的操作系统和编译架构.

特别地，自从G0 1.11，标准Go编译器开始支持WebAssembly做为一种新的架构。请阅读此篇维基文章获取详情。

### 编译器指示（compiler directive）

标准Go编译器支持若干编译器指示。 一个编译器指示以注释的形式`//go:DirectiveName args`出现。 比如我们可以使用go:generate编译器指示来生成代码； 或者使用Go 1.16版本引入go:embed编译器指示来内嵌数据文件。

### 构建编译约束/标签（build constraint/tag）

我们可以使用构建编译约束（或称标签）来让编译器选择性地忽略某些源文件。 选择标签可以出现在源代码文件中的最顶部，也可以出现在源代码文件名（不包含`.go`后缀）的结尾（并用下划线分隔开来）。 注意：Go官方工具链1.17引入的新的`//go:build`指示将逐渐替代`// +build`构建编译约束。

### 更多的编译模式（build mode）

Go官方工具链中的`go build`命令支持更多的编译模式。 运行`go help buildmode`可以列出所有支持的模式，或者查看官方文档来查看这些模式的解释说明。 除了最常用的default模式，plugin（插件）模式可能是另一种用的较多的模式。 我们可以使用`plugin`标准库包中的函数来加载和使用Go插件。