当前位置: 首页 > news >正文

golang的一些技巧

我想设计一个接口 里面有个参数msgtype 我想让它所有的实现 传入的type都只有定义的那几种 有什么办法? 以及 name、isvalid方法

所以“让接口的所有实现只能传某几个固定的 msgtype”这件事,必须靠“接口之外”的编译期机制来完成。
Go 没有枚举,但可以用“类型+私有常量”的技巧,把合法取值锁在包内部,调用方只能引用你已经导出的那几个值,从而达到“枚举”的效果。

下面给出一种官方推荐、零运行时开销、编译期强制的做法:
定义一个“枚举”类型(包外不可实例化)

// msgtype/msgtype.go
package msgtype// 1. 定义一个非导出的基础类型
type msgType uint8// 2. 定义常量,但只导出“值”,不导出类型
const (Text   MsgType = msgType(1) // 文本Image  MsgType = msgType(2) // 图片Voice  MsgType = msgType(3) // 语音
)// 3. 真正给外部用的接口,只接受这个类型
type MsgType = msgType // 把类型别名公开出去,但底层还是私有类型

关键点

msgType 小写,包外代码永远无法自己构造 msgType(4)。
通过类型别名 MsgType 公开出去,外部只能“引用”你已经导出的那几个常量,不能自定义新值。

业务接口定义

// sender/sender.go
package senderimport "your_project/msgtype"type Sender interface {Send(typ msgtype.MsgType, content []byte) error
}

外部调用方代码

package mainimport ("your_project/msgtype""your_project/sender"
)type smsSender struct{}func (smsSender) Send(typ msgtype.MsgType, content []byte) error {// 这里无需再校验 type,因为编译器已经保证它只能是 Text/Image/Voicereturn nil
}func main() {var s sender.Sender = smsSender{}_ = s.Send(msgtype.Text, []byte("hello")) // ✅ 合法// _ = s.Send(msgType(4), []byte("xxx"))   // ❌ 编译失败:msgType 未导出
}

如果后期需要“扩展”
新增类型只需在 msgtype 包再导出一个常量即可,不需要改接口。
如果一定要“运行时兜个底”,可以在 msgtype 包给 MsgType 加一次 IsValid() 方法,但上面这种“私有类型+公开常量”方案已经能在编译期把 99% 的非法值挡在门外,通常不再需要运行时检查。

一句话总结
“把合法取值做成包级私有类型的常量,只导出常量值而不导出构造权限”,
这就是 Go 里实现“接口参数只能取某几个固定值”的惯用手段。

更多 比如

package conststype TargetType intconst (TargetTypePost    TargetType = 1TargetTypeComment TargetType = 2TargetTypePhoto   TargetType = 3TargetTypeAnswer  TargetType = 4TargetTypeSchool  TargetType = 5
)const (InteractionTypeLike = 1 // 互动类型-喜欢InteractionTypeGift = 2 // 互动类型-赠送礼物
)const (LikeTypeNormal = 1 // 普通喜欢LikeTypeRose   = 2 // 玫瑰怦然心动
)const (VisibleToTargetUserYes = 1 // 对target_user可见VisibleToTargetUserNo  = 2 // 对target_user不可见
)var TargetTypeNames = map[TargetType]string{TargetTypePost:    "动态",TargetTypeComment: "评论",TargetTypePhoto:   "照片",TargetTypeAnswer:  "快问快答",TargetTypeSchool:  "学校",
}const (GiftStatusPending  = 1GiftStatusAccepted = 2GiftStatusRejected = 3
)func (t TargetType) IsValid() bool {switch t {case TargetTypePost, TargetTypeComment, TargetTypePhoto, TargetTypeAnswer, TargetTypeSchool:return truedefault:return false}
}func (t TargetType) Name() string {return TargetTypeNames[t]
}

测试函数的常见错误

✅ 1. 测试函数没有被识别
Go 的测试函数必须满足以下条件:
函数名以 Test 开头;
参数为 *testing.T;
文件名为 _test.go 结尾;
包名为 xxx_test 或原包名(但推荐用 xxx_test 做黑盒测试)。
✅ 你这些条件都满足了,所以不是这个问题。
❌ 2. 容器初始化失败:container.GetIM 返回 nil
这是最常见的问题。
🔍 原因:
你用了 container.GetIM,这通常是一个依赖注入容器(比如 wire、dig、fx 或自研的容器)。
如果容器里没有注册名为 “IM” 的 IM 类型实例,Get 会返回 nil,然后你调用 imClient.SendMsgToOne(…) 就会空指针 panic。
✅ 解决方法:
确保你在测试初始化时正确注册了 IM 实例到容器中。
例如:
go
复制
func TestMain(m *testing.M) {
// 初始化容器
container.Register(“IM”, func() IM {
return NewIMClient() // 或 mock 的实现
})

os.Exit(m.Run())

}

匿名结构体

golang没有匿名结构体语法
匿名结构体语法错误:
go
复制
MsgContent: struct {
ReplySource : ReplySourceInfo struct{},
},
这是非法的 Go 语法。你不能在结构体字面量里用 : 来声明字段类型,也不能嵌套 struct{} 这种写法。

http://www.dtcms.com/a/490747.html

相关文章:

  • 高性能 Go 语言带 TTL 的内存缓存实现:精确过期、自动刷新、并发安全
  • ML.NET机器学习框架基本流程介绍
  • Day32_【 NLP _2.RNN及其变体 _(2) LSTM】
  • 重庆建站模板代理怎么做p2p网站
  • iis配置网站是什么网站建设方案书阿里云模板
  • 【计算机视觉】SAM 3 技术深潜:从“分割万物”到“理解概念”的范式转移
  • 「深度学习笔记3」概率论深度解析:从不确定性到人工智能的桥梁
  • 齐河专业企业网站建设做网站引流到天猫
  • 技术贴!【谷歌浏览器】实用工具推荐之谷歌浏览器(Google Chrome)离线纯净版完全安装指南:告别广告与捆绑骚扰
  • Centos7 自建Umami-开源免费的网站访问流量统计分析平台
  • 申威架构安装Java 11 RPM包教程:java-11.0.7-swjdk-11u-8.ky10.sw_64.rpm详细安装步骤
  • 【STM32项目开源】基于STM32的人体健康监测系统
  • 一个做礼品的网站国外网站用什么dns
  • 东莞 网站建设网站定制制作公司
  • Python 线程 类比c++【python】
  • 舆情监测的底层逻辑与技术方法探析
  • 谈谈redis的持久化
  • 网站建设进度深圳网站建设制作营销
  • SSM高校学生社团管理系统n4pcu(程序+源码+数据库+调试部署+开发环境)带论文文档1万字以上,文末可获取,系统界面在最后面。
  • 强化学习_Paper_2000_Eligibility Traces for Off-Policy Policy Evaluation
  • Kubernetes秘钥与配置管理全解析
  • Python 匿名函数、map、filter、sort 用法详解
  • wordpress 4.0 伪静态seo优化一般优化哪些方面
  • 上海自助模板建站wordpress被黑
  • 数据可视化延迟实时大屏优化:WebSocket增量传输+Canvas渲染数据延迟压缩至300ms
  • TimerFd Epoll
  • 百度网盘怎么实现不限速的高速下载?
  • UltraEdit做网站教程定制开发网站如何报价单
  • 《彻底理解C语言指针全攻略(5)--指针和函数专题》
  • 广州做网站找哪个公司好建设网络道德教育网站不包括