美文网首页
go 利用unsafe.Pointer和uintptr 给私有变

go 利用unsafe.Pointer和uintptr 给私有变

作者: 夏依旧微凉啊 | 来源:发表于2019-10-07 16:10 被阅读0次
    • 定义类型 及访问是有变量的方法
    package p
    
    import "fmt"
    
    type V struct {
        i int
        j string
        k float64
    }
    
    // 此处不用V,否则this 会是调用者的复制,而不是原对象
    func (this *V) PutIPtr() {
        fmt.Println(fmt.Sprintf("v.i ptr:%p", &this.i))
    }
    
    func (this V) PutI() {
        fmt.Println(fmt.Sprintf("V.i:%d", this.i))
    }
    
    func (this V) PutJ() {
        fmt.Println(fmt.Sprintf("V.j:%s", this.j))
    }
    
    func (this V) PutK() {
        fmt.Println(fmt.Sprintf("V.j:%f", this.k))
    }
    
    
    • 在外面赋值
    package main
    
    import (
        "fmt"
        "myself/go-ptr/p"
        "unsafe"
    )
    
    func main() {
        // 初始化内存,返回p.V类型的一个指针
        v := new(p.V)
    
        // v 的地址也是v.i的地址
        fmt.Println(fmt.Sprintf("new ptr:%p", v))
        v.PutIPtr()
        i := (*int)(unsafe.Pointer(v))
        *i = 66
    
        // uintptr(unsafe.Sizeof(int(2))) 获取int类型的指针长度
        // v 指针地址的基础上加上int类型长度,为v.j的地址
        j := (*string)(unsafe.Pointer(uintptr(unsafe.Pointer(v)) + uintptr(unsafe.Sizeof(int(2)))))
        *j = "this is string"
        k := (*float64)(unsafe.Pointer(uintptr(unsafe.Pointer(j)) + uintptr(unsafe.Sizeof(string("22")))))
        *k = 99
        v.PutI()
        v.PutJ()
        v.PutK()
    }
    
    

    *运行结果

    new ptr:0xc000004480
    v.i ptr:0xc000004480
    V.i:66
    V.j:this is string
    V.j:99.000000
    

    相关文章

      网友评论

          本文标题:go 利用unsafe.Pointer和uintptr 给私有变

          本文链接:https://www.haomeiwen.com/subject/sbhwyctx.html