`go vet`要求显式指定`sql.null*`结构体字段名,因其导出字段名明确且为避免未来api变更风险;而自定义结构体若未启用`-composites`检查则默认不警告。
在 Go 语言中,database/sql 包提供的 sql.NullInt64、sql.NullString、sql.NullBool 等类型,均为导出结构体(首字母大写),其定义如下:
type NullInt64 struct {
Int64 int64
Valid bool // true if Int64 is not NULL
}虽然该结构体只有两个字段,但 go vet(特别是其 composites 检查器)对标准库中明确定义的结构体启用更严格的字面量校验规则:它强制要求使用具名字段初始化(keyed literals),以提升代码可读性与健壮性。这是因为:
✅ 正确写法(推荐,通过 go vet):
var n = sql.NullInt64{Int64: 42, Valid: true}
var s = sql.NullString{String: "hello", Valid: false} // NULL 字符串❌ 错误写法(触发 unkeyed fields 警告):
var n = sql.NullInt64{42, true} // go vet 报错⚠️ 为什么自定义结构体 Something 不报错?
go vet 默认仅对标准库(如 database/sql、net/http 等)和部分高风险包启用 composites 检查;你的 Something 属于用户定义类型,除非显式启用 -composites 标志(go vet -composites ./...),否则不会检查其字面量。但这不意味着它是最佳实践——为保持一致性与可维护性,建议所有结构体均采用具名初始化:
type Something struct {
Int64 int64
Valid bool
}
//
✅ 更清晰、更安全
s := Something{Int64: 1, Valid: true}? 总结: