Go的代码风格和规范

Go代码风格与规范

Go语言以简洁、一致性和高效性著称,其官方规范(Go Code Review Comments)和工具链(如gofmtgo vet)是代码风格的核心依据。以下是关键要点:


一、格式化工具
  1. gofmt
    所有代码必须通过gofmt自动格式化(如缩进为Tab、运算符间距等)。这是Go社区的强制约定。

    gofmt -w your_file.go  # 自动修复格式
    

  2. goimports
    自动管理包导入(增删未使用的包、按标准分组排序):

    goimports -w your_file.go
    


二、命名规范
  1. 变量/函数

    • 驼峰式parseRequest(非parse_request
    • 短命名优先:局部变量用ir等,但需确保可读性。
    • 避免冗余UserService而非UserServiceInterface
  2. 包名

    • 小写单数package http(非package httputils
    • 避免通用名:如utilcommon(改用具体功能命名)。
  3. 接口名

    • 行为命名Reader(含Read()方法)、Stringer(含String())。

三、错误处理
  1. 显式检查
    错误必须立即处理,禁止忽略:

    data, err := ioutil.ReadFile("file.txt")
    if err != nil {
        return fmt.Errorf("read file failed: %w", err)
    }
    

  2. 错误包装
    使用%w传递上下文(Go 1.13+):

    if err != nil {
        return fmt.Errorf("processing data: %w", err)
    }
    


四、代码结构
  1. 函数长度
    单函数不超过一屏(约50行),过长时拆分为子函数。

  2. 方法接收器

    • 值接收器func (u User) GetName()):适用于不可变类型。
    • 指针接收器func (u *User) UpdateName()):需修改状态时使用。
  3. 包组织

    • 按功能划分:如/user包含model.goservice.go等。
    • 避免循环依赖:通过接口解耦。

五、注释与文档
  1. 公共符号
    所有导出函数、类型必须有//注释(生成godoc):

    // ParseRequest 解析HTTP请求至结构体
    func ParseRequest(r *http.Request) (*Request, error) { ... }
    

  2. 示例代码
    ExampleXXX()函数提供用例:

    func ExampleParseRequest() {
        req := ParseRequest(testRequest)
        fmt.Println(req)
    }
    


六、并发控制
  1. Goroutine生命周期
    确保能安全退出(通过contextdone通道):

    go func(ctx context.Context) {
        select {
        case <-ctx.Done(): // 响应取消
            return
        case data := <-ch:
            process(data)
        }
    }(ctx)
    

  2. 同步原语
    优先用sync.Mutexsync.WaitGroup,避免裸atomic


七、测试规范
  1. 测试文件命名
    测试文件为xxx_test.go,如service_test.go

  2. 表格驱动测试
    用结构体切片组织多用例:

    func TestAdd(t *testing.T) {
        cases := []struct{ a, b, want int }{
            {1, 2, 3},
            {0, 0, 0},
        }
        for _, c := range cases {
            if got := Add(c.a, c.b); got != c.want {
                t.Errorf("Add(%d,%d)=%d, want %d", c.a, c.b, got, c.want)
            }
        }
    }
    


八、其他最佳实践
  • 避免全局变量:通过依赖注入传递状态。
  • 零值可用:如sync.Mutex无需显式初始化。
  • 避免init()函数:易导致隐式依赖,改用显式初始化。

提示:用golangci-lint集成检查工具,自动执行上述规范。

评论
成就一亿技术人!
拼手气红包6.0元
还能输入1000个字符
 
红包 添加红包
表情包 插入表情
 条评论被折叠 查看
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值