Golang 整理1-基本语法
go
/ Golang
编程语言学习
官方提供了教程,中文版的教程地址 可以边练习边学习
语法声明格式
https://blog.go-zh.org/gos-declaration-syntax
从左到右的规则
从左到右的写法与读法,符合读写习惯,尤其对于调用无名称的方法时尤为明显,如: func(a, b int) int { return a+b } (3, 4)
可以从左到右这样读出语义:一个函数,参数是 a
和 b
( int
)类型的,返回值是: int
类型的,函数体是 {return a+b }
,执行该函数传入的参数是 3
和 4
数组类型
定义数组是 var a []int
(英文读法是 array of int
,所以写 []int
仍然是从左到右的方式 ) 但是使用值的时候是: x = a[1]
指针
指针的标识使用 *
,并且由于 *
有乘法的作用,所以定义指针可以: var p *int
但是使用是 *p
而不是 p*
函数参数类型的省略写法
多个相同类型的参数,只有最后一个不可以省略,其他可省略不写
函数多返回值
go
中函数可以返回多个值,而且可以命名返回值,命名的返回值会被视作定义在函数顶部的变量,进行命名的好处是可以当做文档说明,且当函数体比较短时,直接使用 return
后面不带任何具体变量, go
会自动返回命名返回值的变量。长的函数中它们会影响代码的可读性。
package main
import "fmt"
// 返回y,x两个变量
func swap(x, y string) (string, string) {
return y, x
}
func main() {
a, b := swap("hello", "world")
fmt.Println(a, b)
}
package main
import "fmt"
// 通过在返回值中定义了x,y变量,所以x,y 在函数体中不用定义,且返回时直接使用return。另外就是对于函数接收方的变量不一定要用命名返回值一样的名称。比如可以var a,b = split(17) 另外假如只需要使用第一个返回值,可以这样定义:var a,_ = split(17),同理,只使用第二个返回值:var _,b = split(17) 可以看到 _ 的作用就是忽略对应位置的返回值。
func split(sum int) (x, y int) {
x = sum * 4 / 9
y = sum - x
return
}
func main() {
fmt.Println(split(17))
}
变量声明
var
语句可以出现在包或函数级别
使用关键字 var
声明: [var关键字] [变量名称] [变量类型]
如 var a bool
要是多个相同类型的变量: var a,b,c bool
,假如多个不同类型的
package main
import "fmt"
func main() {
var (
a bool
b int
)
// 没有赋值-则打印类型默认值 false 和 0
fmt.Println(a, b)
}
变量赋值
没有明确初始值的变量声明会被赋予它们的 零值。数值类型为0
,布尔类型为false
,字符串为""
(空字符串)。
- 在变量声明时赋值:
var i, j int = 1, 2
因为赋的值是明确的类型,所以可以可以省略为var i,j = 1,2
变量会从初始值中获得类型 - 函数内使用
:=
赋值(只能在函数内且右边的值有明确类型的情况下可以使用)i,j := 1,2
等价于var i,j = 1,2
package main
import "fmt"
func method1() {
// 定义 a,b 变量并初始化
var (
a = 1
b = "method1"
)
fmt.Println(a, b)
}
func method2() {
// 定义 a,b 变量并初始化
a, b := 2, "method2"
fmt.Println(a, b)
}
func method3() {
// 定义 a,b 变量并初始化
var a, b = 3, "method3"
fmt.Println(a, b)
}
func main() {
method1()
method2()
method3()
}
基本类型
bool
布尔类型:true/false
string
字符串类型int
int8
int16
int32
int64
uint
uint8
uint16
uint32
uint64
uintptr
uintptr 是 Go 内置类型,表示无符号整数,可存储一个完整的地址。常用于指针运算,byte
//uint8
的别名rune
//int32
的别名 // 表示一个 Unicode 码点float32
float64
complex64
complex128
⭐️ 需要注意的是 int
, uint
和 uintptr
在 32 位系统上通常为 32 位宽,在 64 位系统上则为 64 位宽
⭐️ Golang
中 string
底层是通过 byte数组
实现的。中文字符在 unicode
下占 2
个字节,在 utf-8
编码下占 3
个字节,而 Golang
默认编码正好是 utf-8
,所以 Golang
处理中文长度时都需要转换为 []rune
,还要注意编码问题。
package main
import (
"fmt"
)
func main() {
str := "你好"
// 6
fmt.Println(len(str))
// 强制转换为 []rune
str_rune := ([]rune)(str)
// [20320 22909]
fmt.Println(str_rune)
// 2
fmt.Println(len(str_rune))
}
定义常量
使用关键字 const
定义常量,常量即:一经定义就不可更改的变量,例如: const World = "世界"
,后面就不能修改 World
的值了。
包
Golang
语言使用 包
管理代码模块,并且一定会有一个入口 main
包及 main
包下面的 main函数
做为启动函数,引入包使用关键字 import
package main
// 引入 fmt 包
import "fmt"
func main() {
fmt.Println("你好")
}
假如引入多个包可以简单写:
package main
// 引入多个包简单写
import (
"fmt"
"math"
)
func main() {
c := math.Sqrt(9)
fmt.Printf("%.1f", c)
}
当引入的包中有冲突的时候可以给引入的包起一个别名,比如上面的例子中,给引入的 math
包起一个别名 m
,则可以这样:
package main
import (
"fmt"
// math 包起一个别名 m
m "math"
)
func main() {
// 使用别名 m 使用 math 包中的方法
c := m.Sqrt(9)
fmt.Printf("%.1f", c)
}
包可以简单理解为一个目录,相对于 main
包下创建一个目录 test
,那么在 test
下新建的 go
文件都是处于 test
包下,在同一个包下方法和变量是可以直接调用的,要是在不同的包之间进行方法及变量等访问,需要把方法或者变量的首字母大写:
package test
// test 包内可以访问 add 方法,但是不会被外部的包访问到
func add(a, b int) int {
return a + b
}
// Sub 可以被其他包引入后访问到
func Sub(a, b int) int {
return a - b
}