Go问答技术文章
-
解释 Go nil slice 与空但非 nil 的 slice 为什么在传统 encoding/json 中分别输出 null 和 [],并说明 omitempty、响应 DTO 归一化以及 encoding/json/v2 迁移时的边界。364 收藏 -
Go 切片 append 后另一个切片内容跟着变化,通常是因为容量足够时仍共享底层数组。本文用 len、cap 和最小示例区分共享与扩容分支,并给出 copy 与 slices.Clone 的隔离写法。489 收藏 -
Go 的 map 遍历顺序没有语言规范保证,不能直接把 range 结果写进固定断言。本文用独立 key 切片排序的方法生成稳定输出,并说明 nil map、遍历期间修改和生产代码边界。167 收藏 -
Go 的 map 读取不存在的键时不会报错,而是返回元素类型的零值。本文用具体代码解释单值读取、comma-ok、nil map 与写入 panic 的边界。482 收藏 -
Go 方法表达式 T.M 与方法值 x.M 的差别不在语法表面,而在接收者何时绑定。本文用值接收者和指针接收者示例说明函数类型、状态变化与回调选择。370 收藏 -
Go 空接口断言失败通常不是值看起来不对,而是动态类型与目标类型不完全一致。本文用 %T、comma-ok、类型 switch 区分值类型、指针类型和 typed nil。432 收藏 -
Golang · Go问答 | 5天前 | 接口 · Go问答 · 类型比较 · 运行时panic · 动态类型 reflect.Value.Comparable Go接口比较 interface panic
Go 接口类型本身支持比较,但接口里的动态值如果是 slice、map、func,或包含这些字段的数组和结构体,比较相同动态类型的两个接口就可能触发 panic。本文说明判断边界,并给出 reflect.Value.Comparable、reflect.DeepEqual 和类型化比较的选择方法。481 收藏 -
Golang · Go问答 | 5天前 | defer · Go问答 · 代码排查 · 函数返回值 · 命名返回值 Go defer 显式 return 返回值覆盖 named return values
Go defer 会不会覆盖显式 return,关键不在 return 写没写值,而在 defer 是否能访问函数的命名结果参数。本文用执行顺序、闭包捕获和 defer 参数求值三个角度拆开这个常见误区。485 收藏 -
Go defer 不是把整条语句留到函数结束才解释:函数值和参数在登记时求值,真正调用在返回前发生。本文拆开值参数、闭包和命名返回值的时机差异。120 收藏 -
Golang · Go问答 | 5天前 | 并发 · go · atomic.Pointer · 状态设计 · Go atomic.Pointer atomic.Pointer Load Go nil状态
Go atomic.Pointer 的 Load 返回 nil,只能说明当前没有对象,不能区分零值未初始化和曾有对象后被 Store(nil) 清空。本文用额外状态位和 CAS 说明如何设计可判断的生命周期状态。250 收藏 -
atomic.Value 的 Store 参数虽然是 any,但同一个 Value 首次写入后就锁定具体类型。本文用最小复现定位值类型、指针类型和 nil 导致的 panic,并给出稳定快照的修复写法。145 收藏 -
Go sync.Pool 的 Get 不保证返回刚 Put 的对象,池内元素也可能被自动移除。本文用最小代码说明 Get、Put、New 的边界,并给出复用临时对象时的排查清单。336 收藏 -
Go sync.Once.Do 内部函数发生 panic 后不会自动重试;本文用调用计数、recover 和对比表说明 Once、OnceFunc 与显式重试状态机的边界。434 收藏 -
Go 报 sync: negative WaitGroup counter,通常不是 Wait 本身出错,而是某条执行路径让 Done 多于已完成的 Add。本文从计数关系、defer 作用域、错误分支和 helper 责任四个位置定位多余的 Done,并给出可复用的修复写法。366 收藏 -
Go 里把 WaitGroup.Add 写进 goroutine,会让 Wait 有机会在计数建立前先返回。本文用时序拆解根因,给出 Add、Done、Wait 的安全写法,并说明嵌套任务和 WaitGroup.Go 的边界。434 收藏