【问题标题】:Embedding structs in golang gives error "unknown field"在 golang 中嵌入结构会产生错误“未知字段”
【发布时间】:2017-05-31 21:35:37
【问题描述】:

我在user 包中有一个struct,名为account

type Account struct {
    Tp          string `json:"type"bson:"type"`
    AccountId   string  `json:"account_id"bson:"account_id"`
    Credentials map[string]interface{} `json:"credentials,omitempty"bson:"credentials,omitempty"`
    ProfilePicture string `json:"profile_picture,omitempty"`
    Username string `json:"username"bson:"username"`
    AccessToken map[string]interface{}`bson:"access_token,omitempty"`
}

在user/accounts 中,我试图将此帐户结构嵌入到另一个结构中

type returnAccount struct {
    user.Account
    AccessToken string `json:"access_token,omitempty"`
}

在尝试嵌入之前正确导入用户包我已成功使用它

最后在一个循环中,我正在获取用户帐户并制作returnAccount 的地图并从我的函数返回 这是我的功能

func getAccounts(usr *user.AuthenticatedUser, id ...string) (accounts map[string]returnAccount) {
    accounts = make(map[string]returnAccount)
    if len(id) > 0 {
        for _, v := range id {
            for _, acnt := range usr.Accounts {
                if acnt.AccountId == v {
                    accounts[acnt.AccountId] = returnAccount{
                        Tp:       acnt.Tp,
                        AccountId:acnt.AccountId,
                    }
                }
            }
        }
        return
    }
    for _, v := range usr.Accounts {
        accounts[v.AccountId] = returnAccount{
            Tp:       v.Tp,
            AccountId:v.AccountId,
            Username: v.Username,

        }

    }
    return
}

然而这段代码不会在这里编译是错误信息

# sgin/api/user/accounts
api/user/accounts/getaccounts.go:16: unknown returnAccount field 'Tp' in struct literal
api/user/accounts/getaccounts.go:17: unknown returnAccount field 'AccountId' in struct literal
api/user/accounts/getaccounts.go:26: unknown returnAccount field 'Tp' in struct literal
api/user/accounts/getaccounts.go:27: unknown returnAccount field 'AccountId' in struct literal
api/user/accounts/getaccounts.go:28: unknown returnAccount field 'Username' in struct literal

一切似乎都非常简单明了,我不知道为什么会出现此错误,我需要访问 Account 结构的所有成员都已导出

我需要这个字段的原因是我想通过 api 向客户端发送访问令牌而不是秘密,并且我想降低缩进级别

【问题讨论】:

标签: inheritance go struct compiler-errors compilation


【解决方案1】:

你不能直接初始化嵌入类型中的字段,但是你可以这样做:

accounts[v.AccountId] = returnAccount{
    Account: Account{
        Tp:        v.Tp,
        AccountId: v.AccountId,
        Username:  v.Username,
    },
}

或者,如果v 是Account 类型,您可以使用

accounts[v.AccountId] = returnAccount{
    Account: v,
}

【讨论】:

  • 情况并非如此,这将产生一个额外的缩进级别,我需要在 returnAccount 下直接嵌入帐户
  • 缩进无关紧要。这只是展示了如何在文字中设置这些字段,而不是通过单独的分配来进行。如果您不想这样做,则不必这样做,但这与您尝试做的相同。请删除您的反对票,因为此答案是正确的。
  • 除非您编辑该网站不允许我删除投票的问题,关键是帐户结构将随着程序需要更多详细信息而不断增长,我不想将所有更改键入 2 或更多的地方手工不是我喜欢编写程序的方式
  • 你能对你的帖子做一个小改动,这样我就可以投票了,实际上我用你的方式解决了这个问题
  • 你去@nikoss,它终于发生了
【解决方案2】:

您正在尝试初始化复合文字无法实现的提升字段。来自Go spec:

如果 x.f 是表示该字段或方法 f 的合法选择器,则称为提升结构 x 中匿名字段的字段或方法 f。

Promoted 字段的作用类似于结构的普通字段,只是它们不能用作复合字面量中的字段名 结构。

但您可以使用点表示法访问它们:

ra:= returnAccount{}
ra.Tp = acnt.Tp

【讨论】:

  • 这解决了这个问题,虽然我不太明白这个话题,你能不能详细说明一下我检查了规范但意思不是很清楚@hassansin
  • 另请参阅我的答案,了解无需使用单独作业的方法。
猜你喜欢
  • 1970-01-01
  • 2018-12-25
  • 2015-08-27
  • 2020-12-30
  • 1970-01-01
  • 2020-08-13
  • 1970-01-01
  • 1970-01-01
  • 2018-09-21
相关资源
最近更新 更多