我有一个像这样的golang结构:
type MyStruct struct {
Id string
}
和功能:
func (m *MyStruct) id() {
// doing something with id here
}
我还有另外一种结构:
type MyStruct2 struct {
m *MyStruct
}
现在我有一个功能:
func foo(str *MyStruct2) {
str.m.id()
}
但是我在编译时遇到错误:
str.m.id undefined (cannot refer to unexported field or method mypackage.(*MyStruct)."".id
如何正确调用此功能?
谢谢
答案 0 :(得分:83)
来自http://golang.org/ref/spec#Exported_identifiers:
可以导出标识符以允许从另一个标识符访问它 包。如果两者都导出标识符:
- 标识符名称的第一个字符是 Unicode大写字母(Unicode类" Lu");和
- 标识符在包块中声明,或者是字段名称或方法名称。
醇>
所以基本上只有以大写字母开头的函数/变量才能在包外使用。
示例:
type MyStruct struct {
id string
}
func (m *MyStruct) Id() {
// doing something with id here
}
//then
func foo(str *MyStruct2) {
str.m.Id()
}
答案 1 :(得分:4)
如果您将String[] matchRegex = list.split("\\s+");
更改为MyStruct.Id
,则您将无法再访问它以初始化MyStruct.id
,因为MyStruct2
只能通过自己的id
访问包(是first
包)。
这是因为MyStruct
和MyStruct2
位于不同的包中。
要解决此问题,您可以执行以下操作:
包裹first
:
package first
type MyStruct struct {
// `id` will be invisible outside of `first` package
// because, it starts with a lowercase letter
id string
}
// `Id()` is visible outside to `first` package
// because, it starts with an uppercase letter
func (m *MyStruct) Id() string {
return m.id
}
// Create a constructor function to return `*MyStruct`
func NewMyStruct(id string) *MyStruct {
return &MyStruct{
id: id,
}
}
包裹second
:
package second
// Import MyStruct's package
import "first"
type MyStruct2 struct {
// If you don't use `m` here as in your question,
// `first.MyStruct` will be promoted automatically.
//
// So, you can reach its methods directly,
// as if they're inside `MyStruct2`
*first.MyStruct
}
// You can use `Id()` directly because it is promoted
// As if, inside `MyStruct2`
func foo(str *MyStruct2) {
str.Id()
}
// You can initialize `MyStruct2` like this:
func run() {
foo(&MyStruct2{
MyStruct: first.NewMyStruct("3"),
})
}