# 03.6 Go 指针

Go支持指针！**指针**是内存地址，它能够提升代码运行效率但是增加了代码的复杂度，C程序员深受指针的折磨。在`第2章`中当我们讨论不安全的代码时，就使用过指针，这一节哦我们将深入介绍Go指针的一些难点。另外，当你足够了解原生Go指针时，其安全性大可放心。

使用指针时，`*`可以获取指针的值，此操作成为**指针的解引用**，`*`也叫取值操作符；`&`可以获取非指针变量的地址，叫做取地址操作符。

> 通常来说，经验较少的开发者应该尽量少使用指针，因为指针很容易产生难以察觉的bug。

你可以创建一个参数为指针的函数：

> func getPointer(n \*int) {
>
> }

同样，一个函数的返回值也可以为指针：

> func returnPointer(n int) \*int {
>
> }

`pointers.go`展示了如何安全地使用Go指针，该文件分为4部分，其中第一部分是：

> ```go
> package main
>
> import "fmt"
>
> func getPointer(n *int) {
>    *n = *n * *n
> }
>
> func returnPointer(n int) *int  {
>    v := n * n
>    return &v
> }
> ```

`getPointer()`的作用是修改传递来的参数，而无需返回值。这是因为传递的参数是指针，其指向了变量的地址，所以能够将变量值的改变反映到原值上。

`returnPointer()`的参数是一个整数，返回值是指向整数的指针，尽管这样看起来并没有什么用处，但是在第四章中，当我们讨论指向结构体的指针以及其他复杂数据结构时，你就会发现这种操作的优势。

`getPointer()`和`returnPointer()`函数的作用都是求一个整数的平方，区别在于`getPointer()`使用传递来的参数存储计算结果，而`returnPointer()`函数重新声明了一个变量来存储运算结果。

第二部分:

> ```go
> func main() {
>    i := -10
>    j := 25
>
>    pI := &i
>    pJ := &j
>
>    fmt.Println("pI memory:", pI)
>    fmt.Println("pJ memory:", pJ)
>    fmt.Println("pI value:", *pI)
>    fmt.Println("pJ value:", *pJ)
> ```

`i`和 `j`是整数，`pI`和`pJ`分别是指向`i`和`j`的指针，`pI`是变量的内存地址，`*pI`是变量的值。

第三部分:

> ```go
> *pI = 123456
> *pI--
> fmt.Println("i:",i)
> ```

这里我们使用指针`pI`改变了变量`i`的值。

最后一部分代码:

> ```go
>    getPointer(pJ)
>    fmt.Println("j:",j)
>    k := returnPointer(12)
>    fmt.Println(*k)
>    fmt.Println(k)
>
> }
> ```

根据前面的讨论，我们通过修改`pJ`的值就可以将改变反映到`j`上，因为`pJ`指向了`j`变量。我们将`returnPointer()`的返回值赋值给指针变量`k`。

运行`pointers.go`的输出是：

> $ go run pointers.go
>
> pI memory: 0xc420014088 pJ memory: 0xc420014090 pI value: -10 pJ memory: 25 i: 123455 j: 625 144 0xc4200140c8

你可能对`pointers.go`中的某些代码感到困惑，因为我们在第六章才开始讨论函数及函数定义，可以去了解关于函数的更多信息。


---

# Agent Instructions: Querying This Documentation

If you need additional information that is not directly available in this page, you can query the documentation dynamically by asking a question.

Perform an HTTP GET request on the current page URL with the `ask` query parameter:

```
GET https://wskdsgcf.gitbook.io/mastering-go-zh-cn/3-go-ji-ben-shu-ju-lei-xing/03.6.md?ask=<question>
```

The question should be specific, self-contained, and written in natural language.
The response will contain a direct answer to the question and relevant excerpts and sources from the documentation.

Use this mechanism when the answer is not explicitly present in the current page, you need clarification or additional context, or you want to retrieve related documentation sections.
