美文网首页
Go 基础 5:interface, method和embedd

Go 基础 5:interface, method和embedd

作者: 听海吹牛逼的声音 | 来源:发表于2019-02-10 14:19 被阅读0次

interface和method再java中的概念基本一样。但是go这里不需要显示的说明,只需要默默的实现,有好处也有坏处。
下面是个小例子。只要一个struct实现了interface的所有方法,就可以把这个struct赋值给一个interface。
注意在实现的时候尽量用指针,不然struct内有变量的话,每次调用方法其实是真正你想修改的副本,这个涉及到interface的原理。每次在调用的时候,你的括号里的结构体或者其指针会作为一个参数传递进去,go是基于值传递的,所以传递的是副本,你怎么修改里面的,其实都是修改的副本。

type (
    Processer interface {
        Set(int)
        Get() int
    }

    ProcesserImpl struct {
        val int
    }
)

func (p *ProcesserImpl) Set(v int) {
    p.val = v
}

func (p *ProcesserImpl) Get() int {
    return p.val
}

func main() {
    var p Processer
    p = new(ProcesserImpl) // or &ProcesserImpl{}
    p.Set(1)
    fmt.Println(p.Get())
}

另外go提供了比较有意思的embedding的功能,就是简单的处理方法能让另外一个struct具备这个struct的所有方法。
下面的例子中,SuperProcesser直接可以用Set和Get方法了,而不需要再去访问他内部的ProcesserImpl。

type (
    Processer interface {
        Set(int)
        Get() int
    }

    ProcesserImpl struct {
        val int
    }

    SuperProcesser struct {
        *ProcesserImpl
    }
)

func (p *ProcesserImpl) Set(v int) {
    p.val = v
}

func (p *ProcesserImpl) Get() int {
    return p.val
}

func main() {
    p := SuperProcesser{&ProcesserImpl{}}
    p.Set(10)
    fmt.Println(p.Get())
}

interface如果是空的,那你可以传任何值。然后用type assertion和type switch来判断类型。

type Empty interface{
}

func TestType(e Empty) {
    if v, ok := e.(int); ok {
        fmt.Println(v, ok)
    } else {
        fmt.Println("not int", e)
    }
}

func SwitchType(e interface{}) {
    switch v := e.(type) {
    case int:
        fmt.Println(v, "I am int")
    case string:
        fmt.Println(v, "I am string")
    }
}

func main() {
    TestType(1)
    TestType("test")
    SwitchType(1)
    SwitchType("haha")
}

相关文章

网友评论

      本文标题:Go 基础 5:interface, method和embedd

      本文链接:https://www.haomeiwen.com/subject/kszteqtx.html