嵌入式结构 [英] Embedded struct

查看:74
本文介绍了嵌入式结构的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

是否可以在不使用嵌入式结构的情况下继承类型的方法?

Is it possible to inherit methods of a type without using embedded structs?

第一段代码是将Property结构嵌入到Node中的工作代码,我可以调用node.GetString,这是Properties上的一种方法.我不喜欢这样的事情是当我初始化Node时,我具有(?)来初始化其中的Properties结构.有没有解决的办法?

The first snippet of code is working code that embeds the Property struct in Node and I'm able to call node.GetString that's a method on Properties. The thing I don't like about this is when I initialize Node I have(?) to initialize the Properties struct within it. Is there a way around this?

package main

import "fmt"

type Properties map[string]interface{}

func (p Properties) GetString(key string) string {
    return p[key].(string)
}

type Nodes map[string]*Node

type Node struct {
    *Properties
}

func main() {
    allNodes := Nodes{"1": &Node{&Properties{"test": "foo"}}} // :'(
    singleNode := allNodes["1"]
    fmt.Println(singleNode.GetString("test"))
}

最终,我想做类似以下的事情.其中NodeProperties类型,并且初始化也不需要初始化Property结构.以下代码不起作用,但可能清楚我的目标是什么.

Ultimately, I would like to do something like the following. Where Node is of type Properties and initializing does not require initializing a Property struct too. The following code doesn't work but may be clear what my goal is.

package main

import "fmt"

type Properties map[string]interface{}

func (p Properties) GetString(key string) string {
    return p[key].(string)
}

type Nodes map[string]*Node

type Node Properties

func main() {
    allNodes := Nodes{"1": &Node{"test": "foo"}} // :)
    singleNode := allNodes["1"]
    fmt.Println(singleNode.GetString("test")) // :D
}

我将添加更多使用Properties方法的结构,这就是我要问的原因.如果我只有Node,那么我将只有用于Node的方法并完成.但是因为我将拥有超过Node的资源,所以我发现将相同的方法添加到所有嵌入Properties

I'll be adding more structs that will use Properties's methods which is why I'm asking. If I only had Node, I would just have methods for Node and be done. But because I'll have more than Node I find it kind of redundant to add the same methods to all the structs that embed Properties

对于确切的问题,我想更多了,我想使用Node中的Properties方法,而不必初始化Properties.

I guess more to the exact problem, I want to use Properties methods from Node without having to initialize Properties.

推荐答案

因此,您在这里遇到了Go的特质.嵌入是一个结构中的方法可以被提升"以使其似乎存在于另一个结构中的唯一方法.虽然type Node Properties应该在Node上公开Properties方法,这很直观,但是该语法的作用是使Node承担Properties的内存布局,而不是其任何方法.

So you're running into an idiosyncrasy of Go here. Embedding is the only way in which methods of one struct can get "promoted" to appear to exist on another struct. While it feels intuitive that type Node Properties should expose the Properties methods on Node, that effect of that syntax is for Node to take on the memory layout of Properties but not any of its methods.

它没有解释为什么做出这种设计选择,但是 Go Spec 位于如果干燥,则最不具体.如果您完全按照原样阅读它,没有任何解释,那么它是非常准确的:

It doesn't explain why this design choice was made but the Go Spec is at least specific if dry. If you read it exactly as it appears, with no interpretation, it is very accurate:

接口类型的方法集是其接口.任何其他类型T的方法集都包含所有已声明的方法 接收器类型为T

The method set of an interface type is its interface. The method set of any other type T consists of all methods declared with receiver type T

GetString的接收器类型为Properties而不是Node,认真地,将规范解释为您是没有想象力的会计师.这么说:

GetString has a receiver of type Properties not Node, seriously, interpret the spec like you're an accountant with no imagination. With that said:

其他规则适用于包含匿名字段的结构,如有关结构类型的部分所述.

Further rules apply to structs containing anonymous fields, as described in the section on struct types.

...

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

A field or method f of an anonymous field in a struct x is called promoted if x.f is a legal selector that denotes that field or method f.

提升字段的行为类似于结构的普通字段,除了它们 不能用作结构的复合文字中的字段名称.

Promoted fields act like ordinary fields of a struct except that they cannot be used as field names in composite literals of the struct.

给定一个结构类型S和一个名为T的类型,提升的方法是 包含在该结构的方法集中的方法如下:

Given a struct type S and a type named T, promoted methods are included in the method set of the struct as follows:

  • 如果S包含匿名字段T,则S和* S的方法集 包括接收方T的提升方法.* S的方法集也 包括带有接收器* T的改进方法.
  • 如果S包含匿名 字段* T,S和* S的方法集都包含提升的方法 接收者为T或* T.
  • If S contains an anonymous field T, the method sets of S and *S both include promoted methods with receiver T. The method set of *S also includes promoted methods with receiver *T.
  • If S contains an anonymous field *T, the method sets of S and *S both include promoted methods with receiver T or *T.

关于复合文字的这一行迫使您在创建的每个Node中声明Properties.

That line about composite literals is this thing that forces you to declare Properties inside every Node you create.

p.s.杰夫,你好!

p.s. Hi Jeff!

这篇关于嵌入式结构的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆