Тип интерфейс определяется набором сигнатур его методов.
Значение типа интерфейса может содержать любое значение, реализующее эти методы.
package main
import (
"fmt"
"math"
)
type Abser interface {
Abs() float64
}
func main() {
var a Abser
f := MyFloat(-math.Sqrt2)
v := Vertex{3, 4}
a = f // a MyFloat реализует Abser
a = &v // a *Vertex реализует Abser
fmt.Println(a.Abs())
}
type MyFloat float64
func (f MyFloat) Abs() float64 {
if f < 0 {
return float64(-f)
}
return float64(f)
}
type Vertex struct {
X, Y float64
}
func (v *Vertex) Abs() float64 {
return math.Sqrt(v.X*v.X + v.Y*v.Y)
}
Вывод:
5
В следующем примере на строке 22 есть ошибка. Vertex (тип значения) не реализует интерфейс Abser, потому что метод Abs объявлен только для *Vertex (для указателя на тип).
package main
import (
"fmt"
"math"
)
type Abser interface {
Abs() float64
}
func main() {
var a Abser
f := MyFloat(-math.Sqrt2)
v := Vertex{3, 4}
a = f // a MyFloat реализует Abser
a = &v // a *Vertex реализует Abser
// На следующей строке, v является Vertex (не *Vertex)
// и не реализует Abser.
a = v
fmt.Println(a.Abs())
}
type MyFloat float64
func (f MyFloat) Abs() float64 {
if f < 0 {
return float64(-f)
}
return float64(f)
}
type Vertex struct {
X, Y float64
}
func (v *Vertex) Abs() float64 {
return math.Sqrt(v.X*v.X + v.Y*v.Y)
}
Вывод:
prog.go:22:4:
cannot use v (type Vertex) as type Abser in assignment:
Vertex does not implement Abser
(Abs method has pointer receiver)
Интерфейсы реализуются неявно
Тип реализует интерфейс путем реализации всех его методов. Нет явного объявления о намерении реализовать интерфейс, и нет ключевого слова "implements".
Неявные интерфейсы отделяют объявление интерфейса от его реализаций, которые могут находиться в любом другом пакете без предварительных согласований.
package main
import "fmt"
type I interface {
M()
}
type T struct {
S string
}
// Этот метод означает, что тип T
// реализует интерфейс I,
// но нам не требуется явно обозначать что он делает это.
func (t T) M() {
fmt.Println(t.S)
}
func main() {
var i I = T{"hello"}
i.M()
}
Вывод:
hello
Читайте также:
Комментариев нет:
Отправить комментарий