Map Go函数图

Map Go函数图,map,go,key-value,func,Map,Go,Key Value,Func,我有一个Go程序,它定义了一个函数。我还有一个地图,每个功能都应该有一个键。我该怎么做 我试过这个,但不起作用 func a(param string) { } m := map[string] func { 'a_func': a, } for key, value := range m { if key == 'a_func' { value(param) } } 函数a(参数字符串){ } m:=映射[字符串]函数{ “a_func”:a, } 对于键,

我有一个Go程序,它定义了一个函数。我还有一个地图,每个功能都应该有一个键。我该怎么做

我试过这个,但不起作用

func a(param string) { } m := map[string] func { 'a_func': a, } for key, value := range m { if key == 'a_func' { value(param) } } 函数a(参数字符串){ } m:=映射[字符串]函数{ “a_func”:a, } 对于键,值:=范围m{ 如果键==“a_func”{ 值(参数) } }
你想做这样的事吗?我已经修改了这个示例,以使用不同类型和数量的函数参数

package main

import "fmt"

func f(p string) {
    fmt.Println("function f parameter:", p)
}

func g(p string, q int) {
    fmt.Println("function g parameters:", p, q)
}

func main() {
    m := map[string]interface{}{
        "f": f,
        "g": g,
    }
    for k, v := range m {
        switch k {
        case "f":
            v.(func(string))("astring")
        case "g":
            v.(func(string, int))("astring", 42)
        }
    }
}
如果您知道签名(并且所有函数都有相同的签名),则可以使用
我认为这比使用接口{}

更干净/安全。如果函数是相同的接口,则可以定义类型

package main

import "log"

type fn func (string)

func foo(msg string) {
  log.Printf("foo! Message is %s", msg)
}

func bar(msg string) {
  log.Printf("bar! Message is %s", msg)
}

func main() {
  m := map[string] fn {
    "f": foo,
    "b": bar,
  }
  log.Printf("map is %v", m)
  m["f"]("Hello")
  m["b"]("World")
}

@Seth Hoenig的回答对我帮助最大,但我只想补充一点,Go也接受具有定义返回值的函数:

package main

func main() {
    m := map[string]func(string) string{
        "foo": func(s string) string { return s + "nurf" },
    }

    m["foo"]("baz") // "baznurf"
}

如果你觉得它很难看,你可以使用一种类型(参见@smagch的答案)。

以下是我在我的案例中使用的方法:

主程序包
进口(
“fmt”
)
变量路由映射[string]func()字符串
func main(){
routes=map[string]func()字符串{
“GET/”:主页,
“获取/关于”:关于页面,
}
fmt.Println(“GET/”,pageContent(“GET/”)
fmt.Println(“获取/关于”,页面内容(“获取/关于”))
fmt.Println(“获取/未知”,页面内容(“获取/未知”))
//输出:
//获取/主页
//获取/关于第页
//获取/未知404:未找到页面
}
func pageContent(路由字符串)字符串{
第页,确定:=路线[路线]
如果可以的话{
返回页()
}否则{
返回notFoundPage()
}
}
func homePage()字符串{
返回“主页”
}
func aboutPage()字符串{
返回“关于页面”
}
func notFoundPage()字符串{
返回“404:未找到页面”
}

我使用了一个映射[string]func(a类型,b*类型)我传递了一个字符串来搜索映射,并传递了一个指针来修改切片

希望有帮助

var Exceptions map[string]func(step string, item *structs.Item)

func SetExceptions() {
    Exceptions = map[string]func(a string, i *structs.Item){
        "step1": step1,
    }
}

func RunExceptions(state string, item *structs.Item) {
    method, methBool := Exceptions[state]
    if methBool {
        method(state, item)
    }
}

func step1(step string, item *structs.Item) {
    item.Title = "Modified"
}

这几乎正是我需要的,但假设g需要2个字符串参数。有可能吗?你能详细解释一下“v.(func(string))”;这似乎几乎需要反射包。这里的paren是否进行了任何转换,或者全部都是处理基本接口的?如果不使用f和g作为映射值,您是否可以在那里使用字符串值,而在case“f”下调用f(mapValue):?如果你的函数来自一个结构类型呢?所有的函数都没有相同的签名。事实上,我认为这回答了我上面的问题;我的函数具有相同的签名。但是这里我看到map值是一个带参数的函数。有趣的是,我将尝试这样做,同时只传递要比较的参数。另外,假设函数返回一个字符串变量,它将如下所示:
m:=map[string]func(string,string)string
如何使用类型:。好例子+1。
var Exceptions map[string]func(step string, item *structs.Item)

func SetExceptions() {
    Exceptions = map[string]func(a string, i *structs.Item){
        "step1": step1,
    }
}

func RunExceptions(state string, item *structs.Item) {
    method, methBool := Exceptions[state]
    if methBool {
        method(state, item)
    }
}

func step1(step string, item *structs.Item) {
    item.Title = "Modified"
}