-3
table := s.Model(reflect.New(destType).Elem().Interface()).RefTable()

func (s *Session) Model(dest interface{}) *Session { 
    log.Info(reflect.TypeOf(dest))
    if s.refTable == nil || s.refTable != dest { 
        s.refTable = schema.Parse(dest, s.dialect)
    }
    return s
}

//turns a dest into *Schema
func Parse(dest interface{}, dialect dialect.Dialect) *Schema {
    modelType := reflect.Indirect(reflect.ValueOf(dest)).Type()
    schema := &Schema{
        //Model: modelType,
        Model:    dest, //
        Name:     modelType.Name(),
        FieldMap: make(map[string]*Field), //
    }

    for i := 0; i < modelType.NumField(); i++ {
        p := modelType.Field(i)
        if !p.Anonymous && ast.IsExported(p.Name) {
            field := &Field{
                Name: p.Name,
                //Type: dialect.DataTypeOf(reflect.Indirect(reflect.ValueOf(p.Type))), //
                Type: dialect.DataTypeOf(reflect.Indirect(reflect.New(p.Type))), //
            }
            if t, ok := p.Tag.Lookup("geeorm"); ok {
                field.Tag = t
            }
            schema.FieldNames = append(schema.FieldNames, p.Name) //
            schema.Fields = append(schema.Fields, field)
            schema.FieldMap[p.Name] = field
        }
    }
    return schema
}

This line:table := s.Model(reflect.New(destType).Elem().Interface()).RefTable() Model function parameter is already interface{},why i need to use ".Interface()" convert the value type to interface{}?

Pablo
  • 5
  • 1

1 Answers1

0

Interface is called on a type of reflect.Value. It returns the actual value of the object you're using reflection on. In this particular case, the return value of this call is cast to a concrete type (s.Model), so what it's essentially doing is this:

destTypeValueAsInterface := reflect.New(destType).Elem().Interface()
sModel := s.Model(destValueAsInterface)
table := sModel.RefTable()

In essence, Interface is called to access the destType object, it's cast to the s.Model type (which I suspect is some type Model interface in whatever package s is), so the method RefTable can be invoked.

This kind of reflection is something you see in packages like gorm or marshalling packages (encoding/json and the like). Not knowing what you're trying to do, though, I'd recommend you avoid costly reflection as much as possible by leveraging interfaces and, since go 1.18, generics as much as you possibly can.

Elias Van Ootegem
  • 74,482
  • 9
  • 111
  • 149