golang: 指针和地址

一,指针和地址的操作

1,代码:

要掌握以下三个用法:

    *指针变量名  得到指针所指向的变量
    *类型       表示这是一个此类型的指针
    &变量       返回一个存放变量地址的指针

package main

import (
    "fmt"
    "reflect"
)

func isPointer(v interface{}) bool {
    return reflect.ValueOf(v).Kind() == reflect.Ptr
}

// 定义一个结构体
type Person struct {
    Name string
    Age  int
}


func main() {

    //*指针变量名  得到指针所指向的变量
    //*类型       表示这是一个此类型的指针
    //&变量       返回一个存放变量地址的指针


    //声明指针,打印指针的地址
    person := Person{Name: "Alice", Age: 30}
    ptr1 := &person

    fmt.Println("ptr1是否指针:", isPointer(ptr1))
    fmt.Printf("ptr1指针本身的地址:%p\n", &ptr1)
    fmt.Printf("ptr1指向的变量:%v\n", *ptr1)
    fmt.Printf("ptr1指向的变量的地址:%p\n",&*ptr1)

    fmt.Println("name:", (*ptr1).Name)
    fmt.Println("name:", person.Name)
    fmt.Println("name:", (&person).Name)

    var ptr2 *Person = &person

    fmt.Println("ptr2是否指针:", isPointer(ptr2))
    fmt.Printf("ptr2指针本身的地址:%p\n", &ptr2)
    fmt.Printf("ptr2指向的变量:%v\n", *ptr2)
    fmt.Printf("ptr2指向的变量的地址:%p\n",&*ptr2)

    fmt.Println("name:", (*ptr2).Name)
    fmt.Println("name:", person.Name)
    fmt.Println("name:", (&person).Name)

}

 

2,测试效果:

$ go run main.go 
ptr1是否指针: true
ptr1指针本身的地址:0xc0000a0038
ptr1指向的变量:{Alice 30}
ptr1指向的变量的地址:0xc0000b2000
name: Alice
name: Alice
name: Alice

ptr2是否指针: true
ptr2指针本身的地址:0xc0000a0048
ptr2指向的变量:{Alice 30}
ptr2指向的变量的地址:0xc0000b2000
name: Alice
name: Alice
name: Alice

 

二,用指针作为参数

1,例子

package main

import (
    "fmt"
    "reflect"
)

func isPointer(v interface{}) bool {
    return reflect.ValueOf(v).Kind() == reflect.Ptr
}

// 定义一个结构体
type Person struct {
    Name string
    Age  int
}

//参数为值
func fn1(x int) {
    fmt.Println("fn1 x是否指针:", isPointer(x))
    fmt.Printf("fn1 变量x的地址:%p\n", &x)
	x = 10
}

//参数为指针
func fn2(x *int) {
    fmt.Println("fn2 x是否指针:", isPointer(x))
    fmt.Printf("fn2 指针变量x本身的地址:%p\n", &x)
    fmt.Printf("fn2 x指向的变量:%v\n", *x)
    fmt.Printf("fn2 x指向的变量的地址:%p\n",&*x)
	*x = 40
}


func main() {


	var a = 5
	fmt.Printf("变量a的地址:%p\n", &a)

	//fn1 方法内的x是一个复制的值,它的值改变与a无关,a原本的值所以没有变化
	fn1(a)
	fmt.Println("调用fn1后a的值:",a) //输出5;

    //方法内传入的是指针类型,*x指向变量a, 赋值改变了指针对应的内存地址,导致a的值变化
	fn2(&a)
	fmt.Println("调用fn2后a的值:",a) //输出40 ;

}

2,测试效果

$ go run main.go 
变量a的地址:0xc000084040

fn1 x是否指针: false
fn1 变量x的地址:0xc000084048
调用fn1后a的值: 5

fn2 x是否指针: true
fn2 指针变量x本身的地址:0xc000088040
fn2 x指向的变量:5
fn2 x指向的变量的地址:0xc000084040
调用fn2后a的值: 40

 

posted @ 2024-12-14 13:06  刘宏缔的架构森林  阅读(7)  评论(0编辑  收藏  举报