range
range
关键字用于迭代数组、切片、字符串、Map以及通道等数据结构。通过range
可以方便地遍历这些数据结构的元素。
下面是range
的介绍和几个示例:
- 遍历数组或切片:
Go
numbers := []int{1, 2, 3, 4, 5}
for index, value := range numbers {
fmt.Println(index, value)
}
输出:
Go
0 1
1 2
2 3
3 4
4 5
在这个例子中,range
返回两个值,第一个是当前元素的索引,第二个是当前元素的值。我们可以使用这两个值进行需要的操作。
- 遍历字符串:
Go
str := "Hello, World!"
for index, char := range str {
fmt.Println(index, string(char))
}
输出:
Go
0 H
1 e
2 l
3 l
4 o
5 ,
6
7 W
8 o
9 r
10 l
11 d
12 !
在字符串遍历的例子中,range
会返回当前字符的索引和对应的Unicode字符。使用string()
函数将Unicode字符转换为字符串以便打印。
- 遍历Map:
Go
myMap := map[string]int{"apple": 1, "banana": 2, "orange": 3}
for key, value := range myMap {
fmt.Println(key, value)
}
输出:
Go
apple 1
banana 2
orange 3
在Map遍历的例子中,range
会分别返回当前键和对应的值。我们可以使用这两个值进行相应的操作。
函数
在Go语言中,函数是一种执行特定任务的代码块。 Go 语言最少有个 main() 函数。
1.函数的声明 函数声明告诉了编译器函数的名称,参数,和返回类型。 函数定义格式如下:
Go
func name( [parameter list] ) [return_types] {
函数体
解析: 函数声明包含一个函数名,参数列表, 返回值列表和函数体。
- func:函数由关键字 func 声明。左大括号依旧不能另起一行。
- name:函数名称。
- parameter list:参数列表,参数就像一个占位符,当函数被调用时,你可以将值传递给参数,这个值被称为实际参数。参数列表指定的是参数类型、顺序、及参数个数。函数可以没有参数或接受多个参数。注意参数类型在变量名之后。当两个或多个连续的参数是同一类型,则除了最后一个类型之外,其他都可以省略。
- return_types:返回类型,函数返回一列值。return_types 是该列值的数据类型,如(string, string)返回两个字符串。有些功能不需要返回值,如果函数没有返回值,则返回列表可以省略。也就是说,函数可以返回任意数量的返回值。有返回值的函数,必须有明确的终止语句,否则会引发编译错误。 函数可以返回多个值,多返回值必须用括号。如:
Go
func test(x, y int, s string) (int, string) {
// 类型相同的相邻参数,参数类型可合并。 多返回值必须用括号。
n := x + y
return n, fmt.Sprintf(s, n)
}
函数体:代码集合(一般实现一个功能)。函数从第一条语句开始执行,直到执行 return 语句或者执行函数的最后一条语句。
2.函数的调用
在Go语言中,函数的调用非常简单。你可以通过函数名字加上参数列表的方式来调用函数。下面是函数的调用方法:
Go
result := functionName(argument1, argument2, ...)
具体来说,函数调用的步骤如下:
- 准备函数的参数。根据函数定义时所声明的参数类型和数量,准备相应的实际参数值。
- 使用函数名字加上参数列表来调用函数。确保函数名字和参数之间有一个空格。
- 将参数按照声明顺序传递给函数。注意,参数的数量和类型必须与函数定义时的参数一致,否则会引发编译错误。
- 如果函数有返回值,可以使用变量来接收函数的返回值。函数执行完成后,将返回结果赋值给变量。
下面是一个简单的示例:
Go
package main
import "fmt"
func add(a, b int) int {
return a + b
}
func main() {
result := add(3, 4)
fmt.Println(result) // 输出:7
}
在这个示例中,我们定义了一个名为add
的函数,它接收两个整数参数并返回它们的和。在main
函数中,通过add(3, 4)
调用了add
函数,并将返回值赋给了result
变量。最后,使用fmt.Println
打印出result
的值,输出结果为7
。
指针
-
每个变量在运行时都拥有一个地址,这个地址代表变量在内存中的位置。
-
Go 语言的取地址符是 &,放到一个变量前使用就会返回相应变量的内存地址。
以下实例演示了变量在内存中地址:
Go
package main
import "fmt"
func main() {
var a int = 10
fmt.Printf("变量的地址: %x\n", &a )
}
输出结果是变量 a 所在的内存地址。 1.指针的声明
- 一个指针变量指向了一个值的内存地址。
指针声明格式如下:
Go
var var_name *var-type
// 这是一个指向 int 和 float32 的指针
var ip *int /* 指向整型*/
var fp *float32 /* 指向浮点型 */
var-type为指针类型,var_name 为指针变量名,* 号用于指定变量是作为一个指针。
2.指针的使用:
基本流程
- 声明指针变量:可以使用
*
来声明指针变量。例如,var ptr *int
声明了一个名为ptr
的指向整数类型的指针变量。 - 获取变量的地址:使用
&
操作符可以获取一个变量的内存地址。例如,x := 10; ptr := &x
将变量x
的内存地址赋给了指针变量ptr
。 - 访问指针指向的值:使用
*
操作符可以访问指针指向的变量的值。例如,*ptr
表示访问指针ptr
所指向的整数变量的值。 - 修改指针指向的值:通过指针,我们可以修改其指向的变量的值。例如,
*ptr = 20
表示将指针ptr
所指向的整数变量的值修改为20
。
下面是一个示例程序,演示了指针的使用:
Go
goCopy Code
package main
import "fmt"
func main() {
x := 10
ptr := &x // 获取变量x的内存地址赋给ptr
fmt.Println("x:", x)
fmt.Println("ptr:", ptr)
fmt.Println("*ptr:", *ptr) // 访问指针ptr指向的值
*ptr = 20 // 修改指针ptr指向的值
fmt.Println("x:", x) // 输出:20
}
在上述示例中,我们首先声明了一个整数变量x
,然后通过&x
获取x
的内存地址,并将其赋给指针变量ptr
。接着,我们打印出变量x
的值、指针ptr
的值以及*ptr
(即指针ptr
指向的值)。最后,我们修改指针ptr
指向的值为20
,并再次打印出变量x
的值,可以看到它已经被修改为20
。
个人感悟
通过学习和运用range、函数和指针,我发现它们在编写代码中起到了很大的作用,十分方便。Range可以极大地简化对容器元素的迭代,使代码更加清晰易读。函数让代码模块化,易于理解和复用。指针则提供了直接操作变量内存的能力,提高了程序的灵活性和效率。 大家在学习的过程中,可以多尝试尝试编写简单的代码片段来使用range、函数和指针,然后增加点难度,这样就可以更好地理解了。