go build 和 go run 分工明确:go run 用于调试,编译后立即执行且不保留二进制;go build 用于发布,生成独立可执行文件。前者不检查未显式引用的 .go 文件,后者扫描整个 main 包目录;go run . 才加载全部 main 包文件,而 go run main.go 仅处理单个文件。

go build 和 go run 的行为差异必须分清
调试阶段用 go run,发布前必须用 go build——两者根本不是替代关系,而是分工明确。
-
go run main.go只编译并运行当前文件,不生成二进制;go run .才会加载当前目录下所有main包文件(含lib.go等辅助文件) -
go build默认输出名为目录名的可执行文件(如当前目录叫mytool,输出就是mytool),不加-o时不会覆盖已有同名文件,但也不会报错,容易误以为构建失败 -
go run不检查未被显式引用的.go文件;而go build会扫描整个目录下所有属于main包的文件,漏掉package main声明或包名不一致,直接报no Go files in current directory
flag 包解析参数时最容易踩的三个坑
不用第三方库也能写得规范,但 flag 的调用顺序和解引用规则稍不注意就 panic 或读不到值。
- 必须在所有
flag.Xxx()定义之后、使用前调用flag.Parse(),否则*flag.Bool等返回值始终是零值 - 获取值时一定要解引用:
if *verbose而不是if verbose(因为flag.Bool返回的是*bool类型指针) - 短选项(
-v)和长选项(--verbose)默认都支持,但-f file.txt和--file=file.txt是等价的;若混用空格和等号(如--file file.txt),flag会当作两个独立参数处理,第二个被忽略
交叉编译时 CGO_ENABLED=0 不是可选,而是必需
跨平台构建静态二进制(比如 macOS 上编译 Linux 版本),CGO_ENABLED=0 必须显式关闭,否则会因目标系统缺失 libc 而运行失败。
- Linux/macOS 上设置:
CGO_ENABLED=0 GOOS=linux GOARCH=amd64 go build -o mytool-linux . - Windows PowerShell 中要用
$env:CGO_ENABLED="0",CMD 中用SET CGO_ENABLED=0,环境变量大小写敏感,cgO_enabled无效 - 开启
CGO_ENABLED时,go build会尝试链接目标系统的动态库(如libc.so),导致在异构系统上直接报cannot execute binary file: Exec format error
GOBIN 和 PATH 配置不到位,build 出来的工具根本找不到
很多人 go build -o mytool 成功了,却在别处执行不了 mytool,问题不在代码,而在环境。
-
go install会把二进制放到$GOBIN目录(默认为$GOPATH/bin),但前提是项目有go.mod且模块路径合法;普通go build不涉及GOBIN - 想全局调用自己构建的工具,要么把输出路径(如
./bin)加进$PATH,要么直接用绝对路径执行(/full/path/to/mytool) - 检查是否生效:运行
which mytool(macOS/Linux)或where mytool(Windows),没输出就说明PATH没配对
package main 和 func main() 是否真的在同一个文件里、是否被意外注释掉,以及 flag.Parse() 是否漏写——这些错误不报语法问题,只让参数永远读不到。golang免费学习笔记(深入):立即使用
在学习笔记中,你将探索golang的核心概念和高级技巧!











