Golang - 3 go语言变量类型、语句块、可见规则、作用域范围
3 go语言变量类型
1 数字
1.1 int、int8、int16、int32、int64
int类型 | 表示范围 |
---|---|
int | 整数 - 分正负 |
int8 | 1个字节,表示 -128 ~ +127 |
int16 | 2个字节,表示 -2的15次方 ~ +2的15次方 |
int32 | 表示 -2的31次方 ~ +2的31次方 |
int64 | 表示 -2的63次方 ~ +2的63次方 |
1.2 uint、uint8、uint16、uint32、uint64
int类型 | 表示范围 |
---|---|
uint | 正整数 |
uint8 | 1个字节,表示 0 ~ 256 |
uint16 | 2个字节,表示 0 ~ +2的15次方 |
uint32 | 表示 -2的31次方 ~ +2的31次方 |
uint64 | 表示 -2的63次方 ~ +2的63次方 |
1.3 浮点型
浮点型 | 表示范围 |
---|---|
float32 | 小数点后7位 |
float64 | 小数点后16位(只要足够长默认是64) |
var p1 float32 = 12.12345678901234567890
var p2 float64 = 12.12345678901234567890
fmt.Println(p1) // 12.123457
fmt.Println(p2) // 12.123456789012346
1.4 复数
复数 | 表示 |
---|---|
complex64 | |
complex128 |
var a complex64 = 4 + 4i
var b complex64 = 9 + 7i
fmt.Println(a + b) // (13+11i)
1.5 byte和rune
名称 | 表示 |
---|---|
byte | unit8的别名 - ascii码的1个字符长度 |
rune | int32的别名 - unicode的1个字符长度 |
python 中len()函数算的是字节长度
2 字符串
string
- 双引号:字符串
- 单引号:表示一个字符 - 默认使用int32字符串
字符串 没有则返回空字符串
数字类型 则返回0
3 布尔类型
名称 | |
---|---|
true | |
false |
4 常量
常量:恒定不变的常量,定义后值固定不变,不允许修改,用const
关键字定义
- 定义单个
const name string = "duo" // 完整定义后不允许改
const name = "duo"
- 定义多个
// 1 这种方式定义多个,只能为同一类型
const name2,age2 = "duo","12"
// 2 可以定义多个不同类型的常量
const (
loveGod string = "Cupid"
warGod string = "Athens"
godAge int = 100
)
// 3 同时定义多个常量,如果没有赋初值,初值就是上一个的值
const (
a1 = 13
b1 = 12
c
d
e
f
)
fmt.Println(c, d, e, f) //12 12 12 12
5 iota 常量生成器
关键字iota
,创建一些列相关的值,省略逐个定义
(1)定义规则
iota
声明的常量默认会自增1,iota
可理解为const语句块
中的行索引
// iota 常量生成器
const (
a1 = 12
b1 = 12
c = iota
d
e
f
)
fmt.Println(c, d, e, f) //2 3 4 5
// 支持位运算
const (
KB = 1 << (10 * iota)
MB
GB
)
fmt.Println(KB, MB, GB) // 1 1024 1048576
iota注意事项:
- ① iota的使用,必须在
const语句块
中- ② iota 放在第几行,值就是多少,后续的都会自增
6 语句块、可见规则、作用域范围
6.1 语句块
语句块
是指:有由大括号围起来的一个语句序列,比如for循环语句块
,if/else判断语句块
。在语句块
内部声明的变量对外部不可见,块把声明围起来,决定了它的作用域
6.2 可见行规则
包通过 导出
机制控制 变量
、结构体
、函数
等数据可见性
- 可见行规则:
全局可见:首字母大写,可导出
包内可见:首字母小写,不可导出
6.3 作用域范围
(1)全局变量
根据可见行规则,决定在包内可用还是在全局可用
(2)局部变量
① 不同的层级作用域
外层定义的变量在内层可以使用,内层定义的变量外层不可以使用。 常见的 if
, for
等都是不同的代码块, 每个代码块组成了一个层级。
② 内层变量覆盖外层变量
一个程序可以包含多个相同名称的变量,只要这些变量处在不同的语句块内,而内层的会覆盖外出的同名变量
package main
import "fmt"
// 语句块
var phoneVersion string = "12 plus"
func printVersion (){
var phoneVersion string = "11 plus"
fmt.Println(phoneVersion)
}
func main() {
fmt.Println(phoneVersion)
printVersion()
}
-------------
12 plus
11 plus
6.4 包与包导入
包:包是在一个文件夹下
,这个文件夹下所有go文件
的第一行要声明包
关键词:import
① 包内部,首字母小写,不可导出
;大写开头,表示可导出
【函数、变量、结构体】
② 包内部
的变量,只能定义一次
③ 包内部
的东西,在包内部可以直接使用
比如同一个包下,不同go文件中可以直接使用,不用导入
④ 包名可以跟文件夹名不一样,但是一个文件夹下只能有一个包
⑤ 导入包,需要从项目路径开始导入
- 项目结构
day_03
-tools
-s1.go
-s2.go
-go.mod
-s1.go
- 使用别名
// s1.go 中 使用别名来导入 tools包
import aabbc "day_03/tools"
⑥ 包内的init函数,可以使用多次,并在导入包的时候,依次执行
- tools包 - s2.go
package tools
import "fmt"
func init() {
fmt.Println("tools 包下的 s1 下的init 11")
}
func init() {
fmt.Println("tools 包下的 s1 下init 22")
}
func init() {
fmt.Println("tools 包下的 s1 下init 33")
}
- tools包 - s2.go
package tools
import "fmt"
func init() {
fmt.Println("tools 包下的 s2 下的init aa")
}
func init() {
fmt.Println("tools 包下的 s2 下的init bb")
}
- main包下执行 【按照init在包内的位置从上到下依次执行】
tools 包下的 s1 下的init 11
tools 包下的 s1 下init 22
tools 包下的 s1 下init 33
tools 包下的 s2 下的init aa
tools 包下的 s2 下的init bb
⑦ 导入包必须使用,如果只想执行包下的 init函数
,可以使用空白标识符 _
,这样只执行init函数
而不用使用包内的其他东西
import _ "day_03/tools"
tools 包下的 s1 下的init 11
tools 包下的 s1 下init 22
tools 包下的 s1 下init 33
tools 包下的 s2 下的init aa
tools 包下的 s2 下的init bb
go mod
模式从1.11后都是这种模式,项目根路径下会有一个go.mod,包的导入从项目路径下开始导入
go path
模式旧版本的模式,它的包导入,不是从项目路径下开始导入,而是从go path 的src路径下路径下开始导入