如何存储指针指向的地址?

时间:2011-05-31 06:24:25

标签: pointers go

我正在尝试创建一个我创建的对象的地址映射,以及它的分配时间。密钥是调用new()返回的地址。如何获取new()返回的地址?

type T struct{a, b int }

func main(){

        var t int64 = time.Nanoseconds()
        memmap := make(map[uint8]int64)
        fmt.Printf("%d\n", t)
        var ptr *T = new(T)
        ptr.a = 1
        ptr.b = 2
        fmt.Printf("%d %d %p %T\n", ptr.a, ptr.b, ptr, ptr)
        //memmap[ptr] = t //gives error
        //var temp uint8 = ptr//gives error
}

请告诉我地图中关键字段的类型应该是什么,以便我可以存储new()返回的地址?我计划使用不同类型的new(),获取分配的地址并将其与创建时间映射。

2 个答案:

答案 0 :(得分:6)

您可以使用Pointer包中的unsafe类型,也就是说,包名称暗示它,不安全。地址本身是一个不透明的东西,实际上只使用地址值来实现地图的用处很少,最好使用类型和地址的元组。这就是unsafe.Reflect为您提供的。包reflect为您提供了UnsafeAddr功能以及更多功能。

我建议您阅读reflectunsafe软件包的软件包文档。

答案 1 :(得分:3)

使用uintptr,一个足够大的无符号整数来存储指针值的未解释位,作为存储器映射键类型。

例如,

package main

import (
    "fmt"
    "time"
    "unsafe"
)

type T struct{ a, b int }

func main() {
    memmap := make(map[uintptr]int64)

    pT := new(T)
    memmap[uintptr(unsafe.Pointer(pT))] = time.Nanoseconds()
    pT.a = 1
    pT.b = 2
    fmt.Printf("%d %d %p %T\n", pT.a, pT.b, pT, pT)

    pI := new(int)
    memmap[uintptr(unsafe.Pointer(pI))] = time.Nanoseconds()
    *pI = 42
    fmt.Printf("%d %p %T\n", *pI, pI, pI)

    fmt.Printf("\n%T\n", memmap)
    for k, v := range memmap {
        fmt.Printf("%x: %d\n", k, v)
    }
}

输出:

1 2 0xf8400001f8 *main.T
42 0xf8400001f0 *int

map[uintptr] int64
f8400001f0: 1306837191421330000
f8400001f8: 1306837191421293000