zoukankan      html  css  js  c++  java
  • Golang的反射reflect深入理解和示例

    reflect的基本功能TypeOf和ValueOf

    既然反射就是用来检测存储在接口变量内部(值value;类型concrete type) pair对的一种机制。那么在Golang的reflect反射包中有什么样的方式可以让我们直接获取到变量内部的信息呢? 它提供了两种类型(或者说两个方法)让我们可以很容易的访问接口变量内容,分别是reflect.ValueOf() 和 reflect.TypeOf(),看看官方的解释

     reflect.TypeOf()是获取pair中的type,reflect.ValueOf()获取pair中的value,示例如下:
     
    package main
    
    import (
    "fmt"
    "reflect"
    )
    
    func main() {
    var num float64 = 1.2345
    
    fmt.Println("type: ", reflect.TypeOf(num))
    fmt.Println("value: ", reflect.ValueOf(num))
    }
    ./hello 
    type:  float64
    value:  1.2345

    说明

    1. reflect.TypeOf: 直接给到了我们想要的type类型,如float64、int、各种pointer、struct 等等真实的类型

    2. reflect.ValueOf:直接给到了我们想要的具体的值,如1.2345这个具体数值,或者类似&{1 "Allen.Wu" 25} 这样的结构体struct的值

    3. 也就是说明反射可以将“接口类型变量”转换为“反射类型对象”,反射类型指的是reflect.Type和reflect.Value这两种

     

    从relfect.Value中获取接口interface的信息

    当执行reflect.ValueOf(interface)之后,就得到了一个类型为”relfect.Value”变量,可以通过它本身的Interface()方法获得接口变量的真实内容,然后可以通过类型判断进行转换,转换为原有真实类型。不过,我们可能是已知原有类型,也有可能是未知原有类型,因此,下面分两种情况进行说明。

    已知原有类型【进行“强制转换”】

    已知类型后转换为其对应的类型的做法如下,直接通过Interface方法然后强制转换,如下:

     
    realValue := value.Interface().(已知的类型)

    Interface()

    package main
    
    import (
    "fmt"
    "reflect"
    )
    
    func main() {
    var num float64 = 1.2345
    
    pointer := reflect.ValueOf(&num)
    value := reflect.ValueOf(num)
    
    // 可以理解为“强制转换”,但是需要注意的时候,转换的时候,如果转换的类型不完全符合,则直接panic
    // Golang 对类型要求非常严格,类型一定要完全符合
    // 如下两个,一个是*float64,一个是float64,如果弄混,则会panic
    convertPointer := pointer.Interface().(*float64)
    convertValue := value.Interface().(float64)
    
    fmt.Println(convertPointer)
    fmt.Println(convertValue)
    }
     
    x40000160a8
    1.2345
    说明
    1. 转换的时候,如果转换的类型不完全符合,则直接panic,类型要求非常严格!
    2. 转换的时候,要区分是指针还是指
    3. 也就是说反射可以将“反射类型对象”再重新转换为“接口类型变量”

    Golang的反射reflect深入理解和示例

  • 相关阅读:
    Oracle 安装报错 [INS-06101] IP address of localhost could not be determined 解决方法输入日志标题
    Linux下安装oracle数据库提示DISPLAY not set. Please set the DISPLAY and try again。
    redhat 关机注销命令详解
    VirtualBox的四种网络连接方式
    修改RedHat的系统显示时间
    insufficient memory to configure kdump(没有足够的内存)解决方法(待验证、待解决)
    xen坑随笔 heartbeat dpkg垃圾数据库清除
    tomcat 监控脚本
    负载均衡随笔
    GIT命令介绍
  • 原文地址:https://www.cnblogs.com/dream397/p/15039768.html
Copyright © 2011-2022 走看看