Go – run、build、install 编译详解

  • Post author:
  • Post category:其他




一 前言

当完成一个应用的开发以后,往往下一步就是进行源码的编译。如 c 语言 gcc 编译一样,Go 在编译后只有一个二进制的文件,所以可以放到任何可支持的机器部署运行。简直就是“拎包入住”,爽的不要不要的。

在 Go 中和编译有关的命令有三个,它们分别是 go run、go build 和 go install。他们有着相似之处,也有着特殊之处。



二 go run

命令格式:go run [可选参数] 。

命令作用:编译完成并马上运行 Go 程序。

特殊说明:go run

只支持属于 main 包的一个或多个文件作为参数

,不然是不能进行编译的。如下示例:

1. 有一个属于包 hello 的文件 hello.go2. 执行编译 go run hello/hello.go 

然后提示错误:go run: cannot run non-main package

常用参数:

参数名 格式 含义
-o -o file 指定编译后二进制文件名
-importcfg -importcfg file 从文件中读取倒入配置
-s -s 省略符号表并调试信息
-w -w 省略 DWARF 符号表
-buildmode -buildmode mode 设置构建模式 – 默认为 exe
-buildid -buildid id 将ID记录为Go工具链的构建ID
-extld -extld linker 设置外部链接器 – 默认为 clang 或者 gcc
-work -work 设置该参数后不会在程序结束后删掉编译的临时文件,可用于参看编译生成的文件
-n -n 加上该参数可以查看编译的过程,但不会继续执行编译后的二进制文件
-x -x 加上该参数可以查看编译的过程,会继续执行编译后的二进制文件

这里需要对后面两个参数进行额外说明。在使用 go run 编译时候会将二进制文件放到一个临时目录(位置和操作系统或GOTMPDIR有关。),所以想进行查看可以使用 -s 或 -n 命令。这里简单执行如下:

执行:go run -n main.go   

输出:(不同的环境和版本可能有一些区别)

mkdir -p $WORK/b001/
cat >$WORK/b001/importcfg.link << 'EOF' # internal
packagefile command-line-arguments=/Users/ucwords/Library/Caches/go-build/f7/f74031c769cada462e650fd08e00423d8919ea05ae938cfd75d6f99042fa40e1-d
packagefile fmt=/usr/local/go/pkg/darwin_arm64/fmt.a

省略一些输出 ....

packagefile path=/usr/local/go/pkg/darwin_arm64/path.a
EOF
mkdir -p $WORK/b001/exe/
cd .
/usr/local/go/pkg/tool/darwin_arm64/link -o $WORK/b001/exe/main -importcfg $WORK/b001/importcfg.link -s -w -buildmode=exe -buildid=Z9AUzA7WCcfq28wnIXya/tTv-fSkYZRl5cgrbF4U7/JQ3FX5d_Usoe1qtn2xPj/Z9AUzA7WCcfq28wnIXya -extld=clang /Users/ucwords/Library/Caches/go-build/f7/f74031c769cada462e650fd08e00423d8919ea05ae938cfd75d6f99042fa40e1-d
$WORK/b001/exe/main

上面的输出主要干了这些事:

  1. 创建编译依赖需要的临时目录。在编译过程中设置一个临时环境变量 WORK,用于编译的工作区并执行编译后的二进制文件。可以通过 GOTMPDIR 设置。
  2. 编译和生产编译所需的依赖。编译如标准库、外部依赖、自身代码,然后生成、链接对应的归档和编译配置文件。
  3. 创建exe目录。 创建并进入编译二进制需要的零食目录。
  4. 生成可执行文件。
  5. 执行可执行文件。如上列中:$WORK/b001/exe/main。



三 go build

命令格式:go build [可选参数] 。

命令作用:编译指定的源文件、软件包和其他依赖,但是不会在编译后执行二进制文件。

特殊说明:go build 和 go run 在编译过程中其实是差不多的,不同之处是 go build 会生成编译好二进制文件并删掉编译过程产生的临时目录。若没有-o 指定文件名,则和当前目录名一致。

执行: go build -x main.go

输出:
...
...
mv $WORK/b001/exe/a.out main
// 多了这步
rm -r $WORK/b001/ 

常用参数:

参数名 格式 含义
-o -o file 指定编译后二进制文件名
-a -a 强制重新编译涉及的依赖
-s -s 省略符号表并调试信息
-w -w 省略 DWARF 符号表
-p -p 指定编译过程中的并发数,默认为CPU数
-work -work 设置该参数后不会在程序结束后删掉编译的临时文件,可用于参看编译生成的文件
-n -n 加上该参数可以查看编译的过程,但不会继续执行编译后的二进制文件
-x -x 加上该参数可以查看编译的过程,会继续执行编译后的二进制文件



四 go install

命令格式:go install [可选参数] 。

命令作用:编译并安装源文件、软件包,即把编译后的文件(可执行二进制文件、归档文件等)安装到指定的目录中。

特殊说明:将编译后的文件(可执行二进制文件、归档文件等)安装到指定的目录中。若设置了环境变量 GOBIN ,则把二进制可执行文件移到该目录。若禁用 Go modules 则放到 $GOPATH/pkg/$GOOS_$GOARCH下。

执行: go install -x main.go

输出:
...
mkdir -p /Users/ucwords/go/bin/
...
mv $WORK/b001/exe/a.out /Users/ucwords/go/bin/目标目录(go modules的目录名)
rm -r $WORK/b001/ 

常用参数:

参数名 格式 含义
-o -o file 指定编译后二进制文件名
-a -a 强制重新编译涉及的依赖
-s -s 省略符号表并调试信息
-w -w 省略 DWARF 符号表
-p -p 指定编译过程中的并发数,默认为CPU数
-work -work 设置该参数后不会在程序结束后删掉编译的临时文件,可用于参看编译生成的文件
-n -n 加上该参数可以查看编译的过程,但不会继续执行编译后的二进制文件
-x -x 加上该参数可以查看编译的过程,会继续执行编译后的二进制文件



版权声明:本文为m0_51504545原创文章,遵循 CC 4.0 BY-SA 版权协议,转载请附上原文出处链接和本声明。