Go语言圣经2

2.1 命名规则

标识符命名规范:

  1. 首字符必须是 Unicode 字母或下划线 _
  2. 首字符后可跟任意字母、数字、下划线;

2.2 四大声明语句

Go 共 4 种基础声明,分别对应四类实体:

  1. var:变量声明
  2. const:常量声明
  3. type:自定义类型声明
  4. func:函数声明

2.3 变量 var

标准格式

go

运行

复制代码
var 变量名 类型 = 表达式

2.3.1 简短变量声明(语法糖)

:= 简写,自动推导类型,仅能在函数内部使用

go

运行

复制代码
i := 100
i, j := 0, 1

2.3.2 指针

  1. 指针存储另一个变量的内存地址,类型格式 *T
  2. &x:取变量 x 的地址,生成指针;
  3. *p:解引用,访问指针指向的原始变量;

go

运行

复制代码
x := 1
p := &x  // p 是 *int 类型,指向x
*p = 2   // 等价 x=2
fmt.Println(x) // 输出2
  1. 别名特性:指针、slice、map、chan、数组、结构体、接口都会产生底层数据别名,修改一处会同步影响关联引用。

2.3.3 new 函数

new(T) 创建 T 类型匿名变量:

  1. 变量自动初始化为该类型零值;
  2. 返回匿名变量的内存地址,返回值类型 *T

go

运行

复制代码
p := new(int)

2.3.4 变量生命周期

生命周期:程序运行中变量有效存在的时间段(运行时概念)

  1. 包级变量:生命周期 = 整个程序运行周期;
  2. 局部变量:动态生命周期,创建于声明处,无任何引用可达时内存可被 GC 回收。
GC 可达性判定规则

从所有包级变量、当前运行函数局部变量出发,顺着指针 / 引用遍历:

  • 能找到该变量 → 可达,不能回收;
  • 无任何访问路径 → 不可达,GC 可回收。

2.4 赋值

2.4.1 元组赋值

支持一次性同时更新多个变量;空白标识符 _ 可丢弃不需要的返回值:

go

运行

复制代码
_, ok = x.(T)

2.4.2 可赋值性

赋值允许隐式赋值行为;仅当右侧值对左侧变量满足可赋值规则时,赋值合法。

2.5 自定义类型 type

语法:type 新类型名 底层类型

  1. 基于已有底层类型创建全新类型;
  2. 底层结构完全一致,但类型不兼容,用于区分业务概念、增加代码可读性。

2.6 包与文件

包等价于其他语言的库 / 模块,作用:模块化、封装、单独编译、代码复用;规范:一个包内通常仅一个文件编写包注释。

2.6.1 包导入

每个包拥有全局唯一导入路径,通过 import 引入。

2.6.2 包初始化顺序

  1. 先解析包级变量依赖关系;
  2. 按源码书写顺序初始化包级变量;
  3. 多包之间:按导入顺序初始化,每个包仅初始化一次。示例:

go

运行

复制代码
var c = 1    // 最先初始化
var b = f()  // 第二个初始化(依赖c)
var a = b + c// 最后初始化

2.7 作用域

  1. 定义:声明绑定名字,作用域是源代码中该名字可合法使用的文本范围(编译时属性);
  2. 区分概念:
    • 作用域:编译期、文本层面;
    • 生命周期:运行期、内存存活时长;
  3. 句法块:大括号 {} 包裹的代码段(函数体、循环、if 等),是作用域划分核心边界。

补充:语法糖(配套理解笔记)

语法糖:语言提供的简写语法,底层无新逻辑,编译器会自动转为等价基础代码,仅简化书写、提升可读性。例:i := 100 简短变量声明就是标准 var 声明的语法糖。