Given a `[]string` and `map[string]interface{}`, can we traverse the map?

polaris · 2017-02-14 03:00:11 · 586 次点击    
这是一个分享于 2017-02-14 03:00:11 的资源,其中的信息可能已经有所发展或是发生改变。

I'd like to write a function which accepts a slice of keys and returns the result of traversing a map for each of those keys.

For example, given this map:

m := map[string]interface{}{
    "apples":  []string{"delicious", "green", "red"},
    "oranges": map[string]interface{}{
        "foo": 123456,
        "bar": "hello, world",
    },
}

we can get the value of the "bar" key in the "oranges" map by writing:

m["oranges"].(map[string]interface{})["bar"]

We can continue getting at deeply nested keys with the general approach of:

m["first-key"]
  .(map[string]interface{})["second-key"]
  .(map[string]interface{})["third-key"]
  {...}

Now imagine that we have a slice that represents the strings forming the deeply-nested key (e.g. ["oranges", "bar"]), and a map we want to traverse.

Is there a way to write a function which does that? Here's a Go Playground link that I've been working from.


评论:

1lann:

Sure you can, using recursion: https://play.golang.org/p/0-CKUVYsE4

And one using iteration: https://play.golang.org/p/7ze54Hp9vi

DavidDavidsonsGhost:

I prefer your first one, but a type switch is a little cleaner I think: https://play.golang.org/p/zGAA5caVEk

Redundancy_:

As a gentle counterpoint to being able to do it - can you not structure the data better so that it's well-typed and has a semantically consistent meaning?

I realize that this isn't always possible with other people's APIs etc.

jxf:

The map is the result of getting YAML back from a parser in use by a library that I don't control. Since, by definition, YAML represents arbitrarily structured data, it's hard to get more strongly typed than map[string]interface{} without becoming unwieldy.

garaktailor:

How about this: https://play.golang.org/p/WBE14HCqZw

I use something like this when dealing with json that I don't necessarily have a nice schema for.

MohamedBassem:

Some people already answered but I was writing it anyways, so here you go : https://play.golang.org/p/cYldrwU3KA


入群交流(和以上内容无关):加入Go大咖交流群,或添加微信:liuxiaoyan-s 备注:入群;或加QQ群:692541889

586 次点击  
加入收藏 微博
0 回复
暂无回复
添加一条新回复 (您需要 登录 后才能回复 没有账号 ?)
  • 请尽量让自己的回复能够对别人有帮助
  • 支持 Markdown 格式, **粗体**、~~删除线~~、`单行代码`
  • 支持 @ 本站用户;支持表情(输入 : 提示),见 Emoji cheat sheet
  • 图片支持拖拽、截图粘贴等方式上传