1

I tried

func Keys(m map[string]interface{}) []string {
    keys := make([]string, 0, len(m))
    for k := range m {
        keys = append(keys, k)
    }
    return keys
}

but

cannot use m (type map[string]int) as type map[string]interface {} in argument to Keys

I know that golang doesn't support generics, so is it possible to get keys slice uniformly?

can.
  • 2,098
  • 8
  • 29
  • 42

1 Answers1

7

Use the reflect package to get the string keys from a map with arbitrary value type:

func Keys(v interface{}) ([]string, error) {
  rv := reflect.ValueOf(v)
  if rv.Kind() != reflect.Map {
    return nil, errors.New("not a map")
  }
  t := rv.Type()
  if t.Key().Kind() != reflect.String {
    return nil, errors.New("not string key")
  }
  var result []string
  for _, kv := range rv.MapKeys() {
    result = append(result, kv.String())
  }
  return result, nil
}

playground example

Charlie Tumahai
  • 113,709
  • 12
  • 249
  • 242