duangu6588 2017-04-11 16:48
浏览 24

在内存地址调用func

I have a map with a struct as key and a func as value, I would like to call the func when I retrieve the value for a given key

map[struct]func

map[
    {contact %!s(int=1)}:%!s(main.Controller=0x4c7b50) 
    {services/basket %!s(int=2)}:%!s(main.Controller=0x4c7ad0) 
    {categories %!s(int=1)}:%!s(main.Controller=0x4c7ae0) 
    {categories/{category} %!s(int=2)}:%!s(main.Controller=0x4c7af0)
    {categories/{category}/{product} %!s(int=3)}:%!s(main.Controller=0x4c7b00) 
    {basket %!s(int=1)}:%!s(main.Controller=0x4c7b10) 
    {checkout %!s(int=1)}:%!s(main.Controller=0x4c7b40) 
    {sitemap %!s(int=1)}:%!s(main.Controller=0x4c7b30) 
    {services/order %!s(int=2)}:%!s(main.Controller=0x4c7ac0) 
    {services/image %!s(int=2)}:%!s(main.Controller=0x4c7b20) 
    {/ %!s(int=1)}:%!s(main.Controller=0x4c7a00)
]

c := RouteMap[struct]

If I fmt.Printf("%s", c) I get the memory address, how do I invoke the func at the address?

I have tried c() but that gives a runtime error:

%s
0x4c7b10%s
<nil>panic: runtime error: invalid memory address or nil pointer dereference
[signal 0xc0000005 code=0x0 addr=0x0 pc=0x4c76f4]

goroutine 5 [running]:
main.RequestHandler(0x577ce0, 0xc042004018)
        C:/Users/mon/Desktop/server.go:91 +0x684
created by main.main
        C:/Users/mon/Desktop/server.go:41 +0x2a0

EXAMPLE

package main

import (
    "bufio"
    "bytes"
    "fmt"
    "net"
    "strings"
    "time"
)

var RouteMap = make(map[PathIdentifier]Controller)

func main() {
    ln, err := net.Listen("tcp", ":8080")
    if err != nil {
        // handle error
    }

    MapRoute("/", HomeController)
    MapRoute("categories", CategoriesController)
    MapRoute("categories/{category}", CategoryController)
    MapRoute("categories/{category}/{product}", CategoryProductController)
    MapRoute("basket", BasketController)

    MapRoute("checkout", CheckoutController)
    MapRoute("sitemap", SitemapController)
    MapRoute("contact", ContactController)

    MapRoute("services/order", OrderServiceController)
    MapRoute("services/basket", BasketServiceController)
    MapRoute("services/image", ImageServiceController)

    fmt.Printf("%s
", RouteMap)

    for {
        conn, err := ln.Accept()
        if err != nil {
            // handle error
        }
        go RequestHandler(conn)
    }
}

// ----------------------- Request & Response ---------------------------

func ParseQueryString() {}

func ParsePostData() {}

func ResponseHeaders() {}

func ParseRequestHeaders() {}

func RequestHandler(conn net.Conn) {
CrLf := "
"
Terminator := CrLf + CrLf

defer func() {
    //fmt.Println("Closing connection...")
    conn.Close()
}()

timeoutDuration := 10 * time.Second
bufReader := bufio.NewReader(conn)

conn.SetReadDeadline(time.Now().Add(timeoutDuration))

requestBytes, err := bufReader.ReadBytes('
')
if err != nil {
    fmt.Println(err)
    return
}

requestTokens := bytes.Split(requestBytes, []byte(" "))

requestMethod := string(requestTokens[0])
requestPath := string(requestTokens[1])
//requestHTTPVersion := string(requestTokens[2])

if requestMethod == "GET" {
    // Parse path
    pathTokens := strings.Split(requestPath, "/")
    segments := len(pathTokens)

    key := PathIdentifier{path: "categories/{category}/{product}", segments: (segments - 1)}
    c := RouteMap[key]

    fmt.Print("%s
", c)

}

    document := []byte("HTTP/1.1 200 OK" + CrLf + "Date: Mon, 27 Jul 2009 12:28:53 GMT" + CrLf + "Last-Modified: Wed, 22 Jul 2009 19:15:56 GMT" + CrLf + "Content-Length: 49" + CrLf + "Content-Type: text/html" + CrLf + "Connection: Closed" + Terminator + "<html><body><h1>Hello, World!</h1></body></html>" + Terminator)

    conn.Write(document)
}

// ----------------------------- Controller -----------------------------

type Controller func()

type PathIdentifier struct {
    path     string
    segments int
}

func MapRoute(view string, controller Controller) {
    if controller != nil {

        if view != "/" {
            pathTokens := strings.Split(view, "/")

            key := PathIdentifier{path: view, segments: len(pathTokens)}
            RouteMap[key] = controller
            return
        }

        key := PathIdentifier{path: view, segments: 1}
        RouteMap[key] = controller
    }
}

func HomeController() {
    fmt.Print("Invoking the HomeController.
")
}

func OrderServiceController() {

}

func BasketServiceController() {

}

func CategoriesController() {

}

func CategoryController() {

}

func CategoryProductsController() {

}

func CategoryProductController() {

}

func BasketController() {

}

func ImageServiceController() {

}

func SitemapController() {

}

func CheckoutController() {

}

func ContactController() {

}
  • 写回答

1条回答 默认 最新

  • dongwusang0314 2017-04-11 17:37
    关注

    I'm not sure you need to call it "by address". When you call by passing it as a variable, compiler does this for you "under-the-hood". Takes its address and calls it.

    If you wish some level of indirection, you can make:

    M := map[string]func()
    M["function 1"] = F
    // and then call them from map like 
    M["function 1"]()
    
    评论

报告相同问题?

悬赏问题

  • ¥15 虚幻5 UE美术毛发渲染
  • ¥15 CVRP 图论 物流运输优化
  • ¥15 Tableau online 嵌入ppt失败
  • ¥100 支付宝网页转账系统不识别账号
  • ¥15 基于单片机的靶位控制系统
  • ¥15 真我手机蓝牙传输进度消息被关闭了,怎么打开?(关键词-消息通知)
  • ¥15 下图接收小电路,谁知道原理
  • ¥15 装 pytorch 的时候出了好多问题,遇到这种情况怎么处理?
  • ¥20 IOS游览器某宝手机网页版自动立即购买JavaScript脚本
  • ¥15 手机接入宽带网线,如何释放宽带全部速度