Go语言入门基础(二)
阅读本文前,建议已掌握基本C语言语法及规范,本文将更加侧重Go语言和C系列语言的区别以达到快速上手的目的
本文主要参考《Go语言圣经(中文版)》及个人实践撰写,具体可参考: Go语言圣经
本文作为该系列第二篇,将重点介绍程序结构
,具体分为声明
/变量及赋值
/类型
。
声明
在编译原理中对声明语句的作用阐述为“为可执行语句提供信息,以便于其执行”,具体来说定义了对象属性以便执行语句使用。Go语言中有4种声明方式:
声明方式 | 对应实体对象 |
---|---|
var | 变量 |
const | 常量 |
type | 类型 |
func | 函数 |
在实际的Go语言程序编写中,根据声明语句的位置决定其级别,如程序第一行一般都是包声明语句
,后跟的是import包引入(具体已在第一篇文章中介绍);同一级的是包一级声明语句
,相当于C语言中全局变量的位置,注意的是在Go语言中包一级对象可以先使用后声明,使用与声明顺序无严格要求;级别更低的是函数内部级声明
(即局部声明
),严格要求先声明后使用。
以下为示例代码段:
package main
import "fmt"
func main() {
var str1 = "Hello"
fmt.Println(str1)
print_func()
}
func print_func() {
fmt.Println(fl1)
}
const fl1 = 12.1212
运行结果如下:
可以看到包一级声明如函数print_func声明在使用之后,而函数内声明如变量str1,必须先声明后使用,否则编译不通过,如下报错:
变量和常量的声明方式可以直接参考上面的代码,函数的声明方式较为复杂,包括
函数名
+参数列表(可选)
+返回值列表(可选)
+函数体
,注意和C语言书写习惯不同的是Go语言的返回列表单独列在参数列表后,而不是函数名前。以下是圣经中一段经典的温度转换代码:
// Ftoc prints two Fahrenheit-to-Celsius conversions.
package main
import "fmt"
func main() {
const freezingF, boilingF = 32.0, 212.0
fmt.Printf("%g°F = %g°C\n", freezingF, fToC(freezingF)) // "32°F = 0°C"
fmt.Printf("%g°F = %g°C\n", boilingF, fToC(boilingF)) // "212°F = 100°C"
}
func fToC(f float64) float64 {
return (f - 32) * 5 / 9
}
变量及其赋值
变量的创建可以在声明语句中使用var
完成,标准的声明创建格式如下:
var 变量名 类型 = 表达式
其中类型和表达式可以省去任一。Go语言不同于C语言,具有零值初始机制
,即如果省略表达式,会自动初始化为对应数据类型下的零值:
数据类型 | 对应零值 |
---|---|
数值类型 | 0 |
布尔类型 | false |
字符串类型 | 空字符串 |
接口/引用 | nil |
所以Go语言中无论是局部变量还是全局变量,都不会出现C语言中局部变量“未初始化”类的问题和报错。 如果深究其初始化的时间,《Go语言圣经》中做了如下的总结:
初始化表达式可以是字面量或任意的表达式。在包级别声明的变量会在main入口函数执行前完成初始化,局部变量将在声明语句被执行到的时候完成初始化。
为了简化程序书写,Go语言引入了简短变量声明
,作用对象为局部变量
,标准格式如下:
变量名 := 表达式
同样也可以生命一组变量:
in, err := os.Open(infile) //Open函数会返回两个值,文件对象/错误类型分别初始化in/err
如果一组变量中有某个变量已经声明过,那么只有赋值操作,覆盖原值。但是这毕竟是一个“声明”语句,所以一组变量中不能都是已经声明过的变量,否则编译不通过。
和C语言类似,对应于“占位符”作用的变量,Go语言中也有指针
,指向了一个值的内存地址,使用方法(&
和*
)与C语言完全相同。
以下是声明和使用的示例代码:
package main
import "fmt"
func main() {
str1 := "Tongji University"
p_str1 := &str1
fmt.Println(str1)
fmt.Println(*p_str1)
*p_str1 = "Huangdu Institute of Technology"
fmt.Println(*p_str1)
}
运行结果如下:
变量指针的零值为nil,可以通过p!=nil
来判断是否是有效的指针。
和C语言类似,Go语言也可以使用关键字new
给变量申请空间(或称为另一种变量的声明和创建方式),以下是内建new函数的使用方法:
指针名 := new(数据类型)
作用对象为指针,上述代码的实际作用就是创建一个匿名变量,并初始化为零值,和普通变量声明语句方式的创建变量并没有什么区别,可以说是一种语法糖。
声明后变量在程序运行中的赋值
通过赋值运算符=
实现,和C语言的区别是不支持 x=i++ 的操作(i++是语句而不是表达式,赋值号右边必须为表达式)。此外,Go语言还支持元组赋值
,即一个赋值语句给多个对象赋值,使用语法如下:
x , y , z = a[1] , a[2] , a[3]
也可以使用x,y=y,x
的简单语句实现类似于C++中swap
函数的功能,整体来说使用非常方便。
类型
类型使用关键字type
,用于给已有的数据类型起别名,常用于分隔不同概念,作用类似于C语言的typedef,使用方法如下:
type 新类型名 底层类型名
新类型的使用方式和结构完全等同于底层类型,所以不算是一个真正意义上“新”的类型定义。
转载自:https://juejin.cn/post/7186989901152419897