扩展 Go 中的现有类型
Go 中不直接支持扩展外部包中定义的现有类型。但是,有一些解决方法可以实现类似的结果。
让我们考虑问题中提供的示例:
1 2 3 4 5 6 7 8 9 10 11 12 13 14 | package util
import(
"net/http"
"github.com/0xor1/gorillaseed/src/server/lib/mux"
)
func (r *mux.Route) Subroute(tpl string, h http.Handler) *mux.Route{
return r.PathPrefix( "/" + tpl).Subrouter().PathPrefix( "/" ).Handler(h)
}
func (r *mux.Router) Subroute(tpl string, h http.Handler) *mux.Route{
return r.PathPrefix( "/" + tpl).Subrouter().PathPrefix( "/" ).Handler(h)
}
|
登录后复制
尝试编译此代码时,遇到错误:“无法定义非本地类型 mux.Router 上的新方法”。这是因为 Go 不允许从外部包直接扩展类型。
解决方法 1:定义包装类型
一种解决方法是定义一个嵌入的包装结构原始类型并提供所需的方法。例如:
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 | type MyRoute struct {
*mux.Route
}
func (r *MyRoute) Subroute(tpl string, h http.Handler) *mux.Route {
return r.PathPrefix( "/" + tpl).Subrouter().PathPrefix( "/" ).Handler(h)
}
type MyRouter struct {
*mux.Router
}
func (r *MyRouter) Subroute(tpl string, h http.Handler) *mux.Route {
return r.PathPrefix( "/" + tpl).Subrouter().PathPrefix( "/" ).Handler(h)
}
|
登录后复制
解决方法 2:类型断言
另一个选项是使用类型断言将原始类型转换为interface{},然后再转换为a提供所需方法的自定义类型。例如:
1 2 3 4 5 6 7 8 9 10 | func (r interface {}) Subroute(tpl string, h http.Handler) *mux.Route {
switch v := r.(type) {
case *mux.Route:
return v.PathPrefix( "/" + tpl).Subrouter().PathPrefix( "/" ).Handler(h)
case *mux.Router:
return v.PathPrefix( "/" + tpl).Subrouter().PathPrefix( "/" ).Handler(h)
default :
panic( "unreachable" )
}
}
|
登录后复制
注意: 这些解决方法可能会带来额外的复杂性,应谨慎使用。如果可能,最好避免修改外部类型,而是定义自己的类型来包装或扩展您需要的功能。
以上是在不支持直接扩展的情况下如何扩展Go中现有的类型?的详细内容。更多信息请关注PHP中文网其他相关文章!