[英]Reverse a map in <value, key> format in Golang
我的程序有一个 map,如下所示:
fruit_map := map[string]string {
"apple": "likey",
"orange": "no likey",
}
我想反转它,以便它读取以下内容:
{
"likey": "apple",
"no likey": "orange",
}
值中没有重复项。 另外,我的 map 很小——大约 200 个键。 我没有找到任何内置方法来像这样反转 map。 有什么办法可以快速做到这一点? 我不太在意空间复杂性,但解决方案需要快速。
谢谢。
您可以编写一个for
循环来迭代原始地图的键值对,并将它们放入一个新地图中(请参阅函数reverseMap
)
代码@https://play.golang.org/p/5y1gABTpdb8
package main
import (
"fmt"
)
func main() {
fruit_map := map[string]string{
"apple": "likey",
"orange": "no likey",
}
reversedMap := reverseMap(fruit_map)
fmt.Println(reversedMap)
}
func reverseMap(m map[string]string) map[string]string {
n := make(map[string]string, len(m))
for k, v := range m {
n[v] = k
}
return n
}
输出:
map[likey:apple no likey:orange]
顺便说一句,将 go 变量命名为fruit_map
是fruit_map
,你真的应该使用驼峰式fruitMap
,比如fruitMap
。
其他答案提供了基于直接处理地图的简单解决方案。
另一种解决方案是将双向映射封装为一个自包含的实用程序,其优点是您可以为其编写完整的单元测试,然后能够依靠它通过简单的 API 正确运行。
这是我的示例实现(不完整,还没有必要的单元测试):
包主
import (
"fmt"
)
func main() {
biMap := NewBiMap()
biMap.Put("apple", "likey")
biMap.Put("orange", "no likey")
v, _ := biMap.GetByValue("no likey")
fmt.Println(v)
}
type BiMap struct {
ab map[string]string
ba map[string]string
}
func NewBiMap() *BiMap {
return &BiMap{make(map[string]string), make(map[string]string)}
}
func (m *BiMap) Put(key, value string) *BiMap {
m.ab[key] = value
m.ba[value] = key
return m
}
func (m *BiMap) GetByKey(key string) (value string, exists bool) {
value, exists = m.ab[key]
return
}
func (m *BiMap) GetByValue(value string) (key string, exists bool) {
key, exists = m.ba[value]
return
}
func (m *BiMap) Len() int {
return len(m.ab)
}
func (m *BiMap) DeleteKey(key string) *BiMap {
value, exists := m.ab[key]
if exists {
delete(m.ab, key)
delete(m.ba, value)
}
return m
}
func (m *BiMap) DeleteValue(value string) *BiMap {
key, exists := m.ba[value]
if exists {
delete(m.ab, key)
delete(m.ba, value)
}
return m
}
您是对的,没有任何内置功能可以实现这一点,但它非常简单:
package main
import "fmt"
func main() {
fruit_map := map[string]string{
"apple": "likey",
"orange": "no likey",
}
//create your new empty map that will hold your reversed contents.
reversed_fruit_map := make(map[string]string)
for k, v := range fruit_map{
reversed_fruit_map[v] = k
}
fmt.Println(reversed_fruit_map)
}
这将输出以下内容:
map[likey:apple no likey:orange]
在操场上看看。 如果这是常见的,您可以随时提取到您自己的函数中。
没有内置函数可以做到这一点,但是使用for
循环就足够简单了。
fruit_map := map[string]string {
"apple": "likey",
"orange": "no likey",
}
reversed_map := make(map[string]string)
for key,value := range fruit_map {
reversed_map[value] = key
}
使用实现了Reverse()
方法的自定义类型是另一种选择。
package main
import "fmt"
type (
MapA map[string]string
MapB map[int]string
)
// Reverse returns a reverse map of the MapA object.
func (m MapA) Reverse() map[string]string {
n := make(map[string]string, len(m))
for k, v := range m {
n[v] = k
}
return n
}
// Reverse returns a reverse map of the MapB object.
func (m MapB) Reverse() map[string]int {
n := make(map[string]int, len(m))
for k, v := range m {
n[v] = k
}
return n
}
func main() {
myMapA := &MapA{
"apple": "likey",
"orange": "no likey",
}
myMapB := &MapB{
10: "likey",
5: "not sure",
0: "no likey",
}
fmt.Println(myMapA.Reverse())
fmt.Println(myMapB.Reverse())
}
使用通用扩展@Dave C 的答案
package main
import (
"fmt"
)
func main() {
myMap := map[int]string{
1: "one",
2: "two",
3: "three",
}
result := reverseMap(myMap)
fmt.Println(result)
}
func reverseMap[M ~map[K]V, K comparable, V comparable](m M) map[V]K {
reversedMap := make(map[V]K)
for key, value := range m {
reversedMap[value] = key
}
return reversedMap
}
声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.