Я пытаюсь понять код, используемый в моей компании. Я новичок в лангах, и я уже прошел учебник на своем официальном сайте. Тем не менее, я с трудом переношу голову вокруг пустых интерфейсов, то есть интерфейса {}. Из различных источников в Интернете я понял, что пустой интерфейс может содержать любой тип. Но мне сложно определить код, особенно некоторые из функций. Я не буду публиковать здесь все, но только минимальные функции, в которых он был использован. Пожалуйста, несите меня!Использование пустых интерфейсов в go
Function (I am trying to understand):
func (this *RequestHandler) CreateAppHandler(rw http.ResponseWriter, r *http.Request) *foo.ResponseError {
var data *views.Data = &views.Data{Attributes: &domain.Application{}}
var request *views.Request = &views.Request{Data: data}
if err := json.NewDecoder(r.Body).Decode(request); err != nil {
logrus.Error(err)
return foo.NewResponsePropogateError(foo.STATUS_400, err)
}
requestApp := request.Data.Attributes.(*domain.Application)
requestApp.CreatedBy = user
Установка некоторый контекст, RequestHandler
это структура определяется в том же пакете, этот код. domain
и views
являются отдельными пакетами. Приложение представляет собой структуру в домене пакета. Следующие две структуры являются частью взглядов пакета:
type Data struct {
Id string `json:"id"`
Type string `json:"type"`
Attributes interface{} `json:"attributes"`
}
type Request struct {
Data *Data `json:"data"`
}
Следующая являются частью пакета JSON:
func NewDecoder(r io.Reader) *Decoder {
return &Decoder{r: r}
}
func (dec *Decoder) Decode(v interface{}) error {
if dec.err != nil {
return dec.err
}
if err := dec.tokenPrepareForDecode(); err != nil {
return err
}
if !dec.tokenValueAllowed() {
return &SyntaxError{msg: "not at beginning of value"}
}
// Read whole value into buffer.
n, err := dec.readValue()
if err != nil {
return err
}
dec.d.init(dec.buf[dec.scanp : dec.scanp+n])
dec.scanp += n
// Don't save err from unmarshal into dec.err:
// the connection is still usable since we read a complete JSON
// object from it before the error happened.
err = dec.d.unmarshal(v)
// fixup token streaming state
dec.tokenValueEnd()
return err
}
type Decoder struct {
r io.Reader
buf []byte
d decodeState
scanp int // start of unread data in buf
scan scanner
err error
tokenState int
tokenStack []int
}
Теперь я понял, что в STRUCT данных в представлениях пакетов, Приложение будучи установленным как тип для пустого интерфейса. После этого создается указатель на запрос в том же пакете, который указывает на данные переменной.
У меня есть следующие сомнения:
- Что именно
this
ключевое слово означает в Go? Какова цель написанияthis * RequestHandler
? - Инициализация структуры в Go может быть выполнена при присвоении ей переменной путем указания значений всех ее членов. Однако здесь для структуры
Data
назначено только пустое значение интерфейса, а значения для двух других полей не назначены? - В чем преимущество назначения структуры приложения пустующему интерфейсу? Означает ли это, что я могу использовать элементы структуры напрямую с помощью интерфейсной переменной?
- Может ли кто-нибудь помочь мне разобраться в значении этого утверждения?
json.NewDecoder(r.Body).Decode(request)
?
Хотя я знаю, что это слишком много, но мне сложно определить значение интерфейсов в Go. Пожалуйста помоги!