Каковы некоторые примеры интерфейсов Go? - PullRequest
7 голосов
/ 14 ноября 2009

Я нашел интересное сообщение в блоге о Go.

Я пытаюсь понять концепцию интерфейсов, но мне очень трудно это сделать из фрагмента кода в сообщении в блоге и почти невозможно из спецификации языка .

Кто-нибудь может указать на простой пример интерфейсов Go в работающей программе?

Ответы [ 5 ]

4 голосов
/ 14 ноября 2009

Это упражнение для обучения в процессе работы, и, конечно, плохой пример хорошего стиля, но здесь вы идете ( spec ).

Кроме того, в качестве более экзотического примера я сделал пост в списке рассылки офигенных рассуждений об использовании интерфейса {} для создания функций, работающих с анонимными данными (в данном случае, «троичная операция "функция):

package main
import "fmt";
func Tern(exp bool, a interface{}, b interface{}) (interface{}) {
    if exp { return a }
    return b
}
func main() {
    a := 7; b := 1;
    result := Tern(a > b, a, b);
    fmt.Printf("%d\n", result);
}
3 голосов
/ 01 августа 2012

В учебном пособии " Interfaces in Go - часть 2: содействие адаптивному, эволюционному дизайну " (январь 2012 г., от Sathish VJ ) явно упоминается главное преимущество для интерфейсов в Go:

Интерфейсы Go не являются вариантами интерфейсов Java или C #, они намного больше.
Они ключ к крупномасштабному программированию и адаптируемому, эволюционному дизайну .

См. Этот пример из той же статьи о другой перспективе (интерфейсе) для шины:

package main

import "fmt"

//Go Step 1: Define your data structures
type Bus struct {
    l, b, h int
    rows, seatsPerRow int
}

//Go Step 2: Define a real world abstraction that could use the data we structure we have
type Cuboider interface {
    CubicVolume() int
}

//Go Step 3: Implement methods to work on data
func (bus Bus) CubicVolume() int {
    return bus.l *  bus.b * bus.h
}

//Go step - repeat 2 & 3 for any other interfaces
type PublicTransporter interface  {
    PassengerCapacity() int
}

func (bus Bus) PassengerCapacity() int {
    return bus.rows * bus.seatsPerRow
}

func main() {
    b := Bus{
             l:10, b:6, h:3,
             rows:10, seatsPerRow:5}

    fmt.Println("Cubic volume of bus:", b.CubicVolume())
    fmt.Println("Maximum number of passengers:", b.PassengerCapacity())
}

Кажется, что он ориентирован на данные - сначала определите свои данные и постройте абстракции интерфейса по мере продвижения.
Иерархия здесь как бы строится «по пути» без явного указания - в зависимости от сигнатур методов, связанных с типом, это понимается как реализация определенных интерфейсов.

Давайте теперь предположим, что с течением времени некоторые требования к проекту для нашего автобуса изменились - теперь существует новый закон, который гласит, что каждый пассажир должен по крайней мере иметь определенный минимальный объем кубического объема.
Теперь наша шина должна придерживаться нового интерфейса под названием PersonalSpaceLaw, который отличается от любого из других интерфейсов, которые она уже реализует

//new requirement that the Bus must be compatible with
type PersonalSpaceLaw interface {
    IsCompliantWithLaw() bool
}

func (b Bus) IsCompliantWithLaw() bool {
    return (b.l * b.b * b.h) / (b.rows * b.seatsPerRow) >= 3
}

Функциональность была расширена без каких-либо изменений основных классов или основных иерархий. Эта реализация намного чище, легко расширяема и может лучше масштабироваться с изменяющимися потребностями требований проекта.

Вот полная рабочая программа на Go Playground

Статья заканчивается цитатой Джона Асмута из ветки о производительности интерфейсов в Go:

"Это тот факт, что мне не нужно тратить время на разработку какой-то иерархии типов, а затем перестраивать ее два или три раза, прежде чем я закончу.
Дело даже не в том, что это легко сделать правильно -
это тот факт, что мне просто не нужно об этом беспокоиться, и я могу продолжить работу с настоящим алгоритмом."

2 голосов
/ 17 февраля 2011
package main

type Stringer interface {
    String() string
}

type pie int
type pizza string

func (p pie) String() string{
    return "pie"
}

func (p pizza) String() string{
    return "pizza"
}

func main(){
    var a pie
    var b pizza
    fmt.Println(a,b) //fmt.Println() will look for Stringers and call their String() method.
}
0 голосов
/ 09 июня 2013

Википедия объясняет типизацию утки и имеет пример на Go. http://en.wikipedia.org/wiki/Duck_typing

0 голосов
/ 14 ноября 2009

Базовая концепция интерфейсов в Go состоит в том, что любой объект, реализующий метод, определяющий интерфейс, может быть частью этого интерфейса.

Лучший пример - интерфейс Writer. Роб Пайк имеет пример этого в своей вступительной речи в Google Tech Talk (http://www.youtube.com/watch?v=rKnDgT73v8s) - прокрутите до 33:25 в речи для его объяснения.

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...