从导出的函数中返回未导出的类型是否被认为是不好的风格?
当我使用它的时候,我发现它只会制造问题。
一个更好的问题可能是:什么时候从导出的函数中返回未导出的类型是一个好主意。
发布于 2014-01-31 08:41:07
我想说从导出的函数中返回一个未导出的变量并没有什么问题。这就是存取器的定义。
也就是说,只有在每次需要访问未导出的变量时都需要发生一些逻辑的情况下,我才会这样做。
编辑:我希望我能理解你澄清的问题。
如果您有一个未导出的type user struct{}
,并使用NewUser()
返回它,这是否适合您的用例?如果是这样,那么这是一种工厂设计模式,如果你不想让第三方开发人员直接创建user
类型的对象,这在Go中很有用。这样,你的“构造函数”或“工厂”就是获取新实例的唯一地方。
那么,这是“糟糕的风格”吗?我想说,这取决于需要克服的挑战。
发布于 2019-02-23 02:49:25
当你返回一个未导出的类型时,Golang的linters会返回一个警告,所以我想说,虽然这在技术上是可行的,但也是不被鼓励的。1
一个原因是,一些接收未导出类型的代码不能将其用于各种“签名”(例如:类型、函数),而不将其键入为接口(例如: interface{}或其他)。
例如:
package people
type me string
func NewMe() me {
return "me"
}
// in main.go
package main
type eff struct {
m *people.me // <-- cant do this
}
func main() {
var m people.me // <-- cant do this
m2 := people.NewMe() // can do this
}
发布于 2021-07-19 22:41:35
我认为有必要为其他人在这个问题上发表另一种观点。解决这个问题的一种更好的方法是,如果用户打算以任何方式与该类型进行交互,则为该类型定义一个实际的导出接口,或者不返回未导出的类型,这样您就不必处理这种情况。这主要是一个设计问题,让我解释一下。
虽然从技术上讲可以返回未导出的类型,但必须将该类型赋给interface{}
,以便在该包之外的代码使用。对我来说,这是一种代码气味,是我在代码审查中会认真质疑的东西。类似地,我会质疑接受未导出参数的导出函数/方法。
我对此最大的问题是函数签名没有清楚地表达它的使用范围。它是一个内部函数吗,因为它返回一个内部类型?既然它是一个导出函数,那么它是否意味着要被外部使用者调用呢?它真的很模棱两可。
另外,虽然返回interface{}
使得该类型可转移,但它也在一定程度上破坏了类型安全。如果返回interface{}
的目的是为了防止用户在将数据传递给接口的另一部分之前更改数据,则辅助接口需要接受interface{}
,并在使用之前检查有效类型。另外,代码很难闻,编译器也不能帮助我们处理这里的错误调用。
https://stackoverflow.com/questions/21470398
复制相似问题