在Go中,哪种价值反映出来.接口?

lia*_*ggo 13 reflection go

j:=1
Run Code Online (Sandbox Code Playgroud)

Kindj就是reflect.Int,符合市场预期.

var j interface{} = 1
Run Code Online (Sandbox Code Playgroud)

Kindj也是reflect.Int.

哪种价值是reflect.Interface什么?

jos*_*hlf 7

如果您正在寻找一个实用的解决方案,答案很简单,也很烦人.reflect.TypeOf采用一个空的接口类型,您可以将任何数据放入其中.这个问题是接口类型不能容纳另一种接口类型,这意味着你实际上无法传递接口reflect.TypeOf.有一个解决方法,但它有点痛苦.你所要做的是使复合类型(如结构或切片或映射),其中的元素类型之一是接口类型,并提取它.例如:

var sliceOfEmptyInterface []interface{}
var emptyInterfaceType = reflect.TypeOf(sliceOfEmptyInterface).Elem()
Run Code Online (Sandbox Code Playgroud)

即首先创建reflect.Type的表示[]interface{}(的切片interface{}的类型),然后提取元素类型,这是interface{}.

感谢这篇文章.


Gus*_*yer 7

到目前为止,答案似乎令人惊讶地复杂,当问题及其响应实际上是直截了当时:reflect.Interface是一种接口值.

您可以通过以下方式轻松查看:

var v interface{}
var t = reflect.ValueOf(&v).Type().Elem()
fmt.Println(t.Kind() == reflect.Interface)
Run Code Online (Sandbox Code Playgroud)

请注意,ValueOf(v)这不起作用,因为您需要v本身的类型,而不是其内容.


Mos*_*afa 5

好问题.我花了将近一个小时才找到自己!

让我们从这段代码开始:

package main

import (
        "fmt"
        "reflect"
)

// define an interface
type Doer interface {
        Do()
}

// define a type that implements the interface
type T struct{}

func (T) Do() {}

func main() {
        var v Doer = T{}
        fmt.Println(reflect.TypeOf(v).Kind())
}
Run Code Online (Sandbox Code Playgroud)

输出struct不是interface.(你可以在这里运行它.)

那是因为即使我们定义v为接口变量,该变量保存的实际也是类型T.它被称为变量的"动态类型".包的主要要点之一reflect是帮助确定接口变量的动态类型,因此它为您提供动态类型,而不是接口.(即使它想,包reflect无法得到传递给变量的界面TypeOfValueOf,因为变量作为值功能通过.)

所以,你可以看到你的问题"这价值的一种是Interface?",技术上可以用"没有回答 ".

但那有什么Interface好处呢?看到这段代码:

// assuming the above code, just with this main function
func main() {
        a := make([]Doer, 0)
        fmt.Println(reflect.TypeOf(a).Elem().Kind())
}
Run Code Online (Sandbox Code Playgroud)

这打印interface.(这个就在这里.)这个点在函数中Elem,它返回一个map元素的类型,这里是一个接口类型.Elem也适用于指针,数组,切片和通道.获取地图的key(Key)类型,struct的字段(Field和朋友)以及函数的参数和返回参数(InOut)有类似的功能.您可以期望从所有这些获得类型的接口.

Rob Pike写了一篇很棒的文章,反思法则,很好地解释了界面和反思.

  • 2013年8月19日星期一:今天我学到了一些东西. (2认同)

dol*_*men 5

您无法直接获取interface{}值的类型,但可以通过指针间接获取:

reflect.TypeOf(new(interface{})).Elem()
Run Code Online (Sandbox Code Playgroud)

在 play.golang.org 上运行:

t := reflect.TypeOf(new(interface{})).Elem()
fmt.Printf("Type: %s\n", t)
fmt.Printf("Kind: %v\n", t.Kind())
fmt.Printf("IsInterface: %v\n", t.Kind() == reflect.Interface)
Run Code Online (Sandbox Code Playgroud)

输出:

Type: interface {}
Kind: interface
IsInterface: true
Run Code Online (Sandbox Code Playgroud)