go - Restore type information after passing through function as "interface {}"? -


i'm running slight architectural problem golang right that's causing me copy/paste bit more code i'd prefer. feel there must solution, please let me know if perhaps possible:

when pass things through interface {}-typed function parameter, start getting errors such "expected struct or slice", etc. ... though passed struct or slice. realize manually convert these type after receiving them in function, become tedious in instances such this:

local interface type *interface {} can decoded remote interface type; received concrete type

... in case, receiving function seems it'd need hard-coded convert interface {} items respective original types in order work properly, because receiving function needs know exact type in order process item correctly.

is there way dynamically re-type golang interface {} typed variables original type? this, how convert reflect.new's return value original type ... maybe?


edit: clarify, basically, i'm passing &out function , needs original type time reaches inner function call.

example code:

// note: sort of pseudo-golang code, not meant compiled or taken seriously.  func preparetwodifferentthings(keya string, keyb string) {     var somethinga typea;     var somethingb typeb;      loadfromcache(keya, &somethinga, nil);     loadfromcache(keyb, &somethingb, nil);      fmt.printf("somethings: %v, %v", somethinga, somethingb);  }  func loadfromcache(key string, isnew, out interface {}, savenewdata interface {}) {     if err := cache.load(key, &out); err!=nil { // note: current issue expects "&out" `typea`/`typeb` not "interface {}", don't want copy , paste whole function's worth of code or whatever.         panic("oh no!");      }      if (savenewdata!=nil) {         cache.save(key, savenewdata); // doesn't seem care if "savenewdata" "interface {}" when saving, later cache fetches above using "load()" method "interface {}"-typed `&out` parameter throw exception "interface {}" type on `&out` not match original when saved here (`typea`/`typeb`).      }  } 

to change type of interface rightful type, can use type assertions:

package main  import r "reflect"  type struct {     name string }  func main() {     // no pointer     aa := a{"name"}     var ii interface{} = aa      bb := ii.(a)     // main.a      // pointer     := &a{"name"}     var interface{} =      b := *i.(*a)     // main.a      c := i.(*a)     // *main.a      d := r.indirect(r.valueof(i)).interface().(a)     // main.a } 

playground 1

when using type assertions, have know underlying type of interface. in go, there no way use type assertion dynamic type. reflect.type not type, it's interface representing type. no, can't use way.

if have several type possibilities, solution type switch:

package main  import "fmt"  type typea struct {     string }  type typeb struct {     b string }  func dosomethinga(t typea) {     fmt.println(t.a) }  func dosomethingb(t typeb) {     fmt.println(t.b) }  func dosomething(t interface{}) {     switch t := t.(type) {     case typea:         dosomethinga(t)     case typeb:         dosomethingb(t)     default:         panic("unrecognized type")     } }  func main() {     := typea{"i a"}     b := typeb{"i b"}      dosomething(a)     //     dosomething(b)     // b } 

playground 2


Comments

Popular posts from this blog

ios - RestKit 0.20 — CoreData: error: Failed to call designated initializer on NSManagedObject class (again) -

laravel - PDOException in Connector.php line 55: SQLSTATE[HY000] [1045] Access denied for user 'root'@'localhost' (using password: YES) -

java - Digest auth with Spring Security using javaconfig -