为了账号安全,请及时绑定邮箱和手机立即绑定

Golang 数据作为 interface{} 恐慌

Golang 数据作为 interface{} 恐慌

Go
人到中年有点甜 2022-05-23 17:54:16
地鼠,我正在尝试实现 Go 的反射包并且真的坚持一件事。上下文 - 我正在尝试调用一个返回的 API - time.Time 和 interface{} 中的一些数据。该数据大部分可以是 int/int64 或 float32/float64。我在 interface{} 中获取数据并进一步创建一个结构,我将 interface{} 数据保存在 interface 中,因为 reflect 承诺了我可以用接口做的很多花哨的事情type dataStore struct {   CreateTime time.Time   Data interface{}}然后我创建一个map[string][]dataStore来存储来自我获取的 API 的数据。我正在尝试执行以下操作以获取我知道即将到来的 Float64 值,并且我想对它们进行一些数学运算:x := map[string][]dataStore {}ReadDatafromAPI(x) // I call the API to read the data into variable x//Assume map["CA"][]dataStore{{2020-03-31 21:55:52.123456, 123.4567890123e10},}fmt.Println(x["CA"][0].Data) // This prints the data 123.4567890123e10, no problemfmt.Println(reflect.ValueOf(x["CA"][0].Data))// this prints reflect.Valueva := reflect.ValueOf(x["CA"][0].Data) fmt.Println(va.(float64)) // panic: interface conversion: interface {} is reflect.Value, not float64fmt.Println(va.Interface()) // prints 123.4567890123e10fmt.Println(va.Kind()) // prints structfmt.Println(va.NumField()) // prints 2 and I can fetch the fields using Field(0) and Field(1) -- the data doesn't make sense to me. not sure if those are pointers or what我只有一个目标 - 将 float64 获取为 float64,将 int 获取为 int。含义 use 反映了它应该被使用的方式。任何见解将不胜感激。提前致谢。伙计们-感谢所有的答案和指示。我很欣赏这个!看起来我仍然得到 reflect.Value 作为类型,而不是预期的 float64/32。见下文:switch flt := x["CA"][0].Data.(type) {case float64:        fmt.Println("Data is float64 -> ", flt)    fmt.Printf("Type for flt is %T -> ", flt)case float32:        fmt.Println("Data is float32 -> ", flt)    fmt.Printf("Type for flt is %T -> ", flt)default:    fmt.Println("Its default!")    fmt.Printf("Type for flt is %T -> ", flt) // I always get here with reflect.Value as the Type. Never a float64 which is the value store without any question}if nflt, ok := x["CA"][0].Data.(float64); ok {    fmt.Println("nflt is float64")} else {    fmt.Println("nflt is not float64) // I always get to Else}
查看完整描述

2 回答

?
杨__羊羊

TA贡献1943条经验 获得超7个赞

您不需要反射即可将接口转换为已知类型之一。您需要类型断言或类型开关:


if flt, ok:=data.(float64); ok {

   // flt is float64

}

if i, ok:=data.(int); ok {

   // i is int

}

或者:


switch k:=data.(type) {

  case float64:

     // Here, k is float64

  case int:

     // Here, k is int

}


查看完整回答
反对 回复 2022-05-23
?
米琪卡哇伊

TA贡献1998条经验 获得超6个赞

使用双值类型断言来获取值而不会惊慌:


  d, ok := (x["CA"][0].Data.(float64)

  if ok {

     // it's a float64, do something with d.

  }

或使用类型开关:


 switch d := x["CA"][0].Data.(type) {

 case int:

     // d is an int

 case float64:

     // d is a float64

 ... and other types as needed

 default:

     // handle unexpected type

 }


查看完整回答
反对 回复 2022-05-23
  • 2 回答
  • 0 关注
  • 135 浏览
慕课专栏
更多

添加回答

举报

0/150
提交
取消
微信客服

购课补贴
联系客服咨询优惠详情

帮助反馈 APP下载

慕课网APP
您的移动学习伙伴

公众号

扫描二维码
关注慕课网微信公众号