在此之前,搭建了Go的开发环境,并且了解的Go程序的基本结构。选择了一款Go的开发工具。有了这些,现在可以继续探索Go的魅力了。
变量
声明、初始化
在Go中对于变量的声明使用关键字var,这和JavaScript,Pascal一样。在Swift 中var 也用来定义变量,似乎新的语言都倾向使用特别关键字声明变量了。不过变量声明的格式和JavaScript还是有很大的区别,到是有些类似Pascal和Swift–都是类型信息放在变量名之后,区别在于不需要使用:分割。
var v1 int //定义类型为int的变量v1
var v2 string //定义类型为string的变量v2
还可以看出,变量声明语句不需要使用分号作为结束符。现在很多语言在语句结束都摒弃了分号,像Python,Swift,R等等。这点不知道是什么趋势。
Go作为一个比较新的语言,在一些写法上还是有一些比较特殊的做法。像var关键字的另一种用法是可以将若干个需要声明的变量放置在一起。
比如像上面,同时声明v1和v2可以这么写:
var(
v1 int
v2 string
)
在变量声明时可以直接初始化的,这时var关键字甚至可以省略。
var v1 int = 100 //
var v2 = 100 // 编译器可以自动推导出v2的类型
v3 := 100 // 编译器可以自动推导出v3的类型
这里可以看出,第一种方式给出一条警告,鼠标放上去是提示警告信息是“should omit type int from declaration of var v1; it will be inferred from the right-hand side”。意思是应该省略VAR V1的类型为int;它将从右侧来推断。可以看出指定类型已不再是必需的,Go可以从初始化表达式的右值推导出该变量类型,这让Go看起来有点像JavaScript这样的动态类型语言,但Go实际上是一种像java一样的静态类型语言。
第三种引入了一种“:=”符号。这在初始化变量是可以省略var关键字。这个符号应该是Go的独创吧。需要注意的是函数外的每个语句都必须以关键字开始( var 、 func 等等), 因此 := 结构不能在函数外使用。
以上三种方式都是Go支持的,具体使用哪种可以自己选择。
赋值
在Go语法中,变量初始化和变量赋值是两个不同的概念。就像:
var v1 int //定义类型为int的变量v1
v1 = 100 //给v1赋值100
Go语言的变量赋值与其他的编程语言一致,但Go语言中提供多重赋值功能,如要实现交换v1和v2变量的语句。一般做法是需要一个中间变量来完成。temp=v1,v1=v2,v2=temp。但Go可以向下面这样操作。
package main
import "fmt"
func main() {
var v1 int //定义类型为int的变量v1
v1 = 100
var v2 = 200
fmt.Println("v1:", v1)
fmt.Println("v2:", v2)
fmt.Println("交换v1,v2")
v2, v1 = v1, v2
fmt.Println("v1:", v1)
fmt.Println("v2:", v2)
}
常量
定义、声明
常量是指编译期间就已知且不可改变的值。常量的声明与变量类似,只不过是使用 const 关键字。
常量可以是字符、字符串、布尔值或数值。
常量不能用 := 语法声明。
package main
import "fmt"
const Pi = 3.14
func main() {
const World = "世界"
fmt.Println("Hello", World)
fmt.Println("Happy", Pi, "Day")
const Truth = true
fmt.Println("Go rules?", Truth)
}
预定义常量
Go语言预定义了这些常量:true、false和iota。
iota比较特殊,可以被认为是一个可被编译器修改的常量,在每一个const关键字出现时被重置为0,然后在下一个const出现之前,每出现一次iota,其所代表的数字会自动增1。
package main
import "fmt"
func main() {
const ( // iota被重设为0
c0 = iota // c0 == 0
c1 = iota // c1 == 1
c2 = iota // c2 == 2
)
fmt.Println("c0", c0)
fmt.Println("c1", c1)
fmt.Println("c2", c2)
}
如果两个const的赋值语句的表达式是一样的,那么可以省略后一个赋值表达式。因此,上面的前两个const语句可简写为
const ( // iota被重设为0
c0 = iota // c0 == 0
c1 // c1 == 1
c2 // c2 == 2 )
上面两个返回的结果是一样的。
类型
我开始接触Go首先就是先了解Go有哪些类型。
Go语言内置以下这些基础类型:
- 布尔类型:bool
- 整型:int8、byte、int16、int、uint、uintptr等
- 浮点类型:float32、float64
- 复数类型:complex64、complex128
- 字符串:string
- 字符类型:rune
此外,Go语言也支持以下这些复合类型:
- 指针(pointer)
- 数组(array)
- 切片(slice)
- 字典(map)
- 通道(chan)
- 结构体(struct)
- 接口(interface)
- 错误类型:error
布尔类型
在Go语言中的布尔类型与其他语言基本是一致的,关键字为bool,值必须为true或false,不支持自动或强制的类型转换。
整型
整形基本是所有编程语言最基础的类型了。
需要注意的是上图中,像int和int32在Go语言里被认为是两种不同的类型,编译器也不会帮你自动做类型转换。如果要转换需要自己手动做强制转换,强制转换时精度会损失。
对于整型的操作主要有数值计算(+、-、*、/、%),比较运算(>、<、==、>=、<=、!=)。这一点与大多数其他语言相 同,与C、java等完全一致。 而且Go的整型也支持位运算。
浮点型
浮点型用于表示有小数位的数据,Go语言中的浮点类型 采用IEEE-754标准的表达方式。 包括float32和float64两个类型。其中float32等价于C语言的float类型, float64等价于C语言的double类型。
复数类型
复数实际上由两个实数构成,在计算机中用浮点数表示,一个表示实部(real),一个表示 虚部(imag)。 对于一个复数z = complex(x, y),就可以通过Go语言内置函数real(z)获得该复数的实 部,也就是x,通过imag(z)获得该复数的虚部,也就是y。
字符串
字符串是所有编程语言的一种基本类型,Go也不例外。
package main
import "fmt"
func main() {
var str1 string //定义
str1 = "hello" //赋值
char := str1[0] //取得第一个字符
fmt.Printf("字符串%s长度%d\n", str1, len(str1)) //取得第一个字符
fmt.Printf("c字符串%s第一个字符%c\n", str1, char)
str2 := "world" //初始化
fmt.Println(str1 + str2) //字符串连接操作
}
上面对字符串的操作有定义,初始化,赋值,计算长度,取得第一个字符,字符串连接操作。其中取字符串的长度使用了一个Go语言内置的函数len()。还可以看出,Go取字符串字节可以向数组一样,直接通过下标就可以。
字符类型
在Go语言中支持两个字符类型,一个是byte(实际上是uint8的别名),代表UTF-8字符串的单个字节的值;另一个是rune,代表单个Unicode字符。出于简化语言的考虑,Go语言的多数API都假设字符串为UTF-8编码。尽管Unicode字符在标 准库中有支持,但实际上较少使用。
在Go当中 string底层是用byte数组存的,并且是不可以改变的。用string存储unicode的话,即如果有中文,按下标是访问不到的,因为你只能得到一个byte,而汉字需要3个byte。
package main
import "fmt"
func main() {
var str1 string
str1 = "Go语言"
char := str1[2]
fmt.Printf("字符串%s长度%d\n", str1, len(str1))
fmt.Printf("c字符串%s第3个字符%c\n", str1, char)
}
通过输出结果看出,“Go语言”长度是8,因为汉字是按3字节存储的。通过下标取到的也不是想要的“语”字。
这是要想取到想要的结果,就需要使用rune。rune是字节组合。
package main
import "fmt"
func main() {
var str1 string
str1 = "Go语言"
r := []rune(str1)
fmt.Printf("字符串%s长度%d\n", str1, len([]rune(str1)))
fmt.Printf("c字符串%s第3个字符%c\n", str1, r[2])
}
这样就取到了想要的结果。
这里就先到这里,上面是Go支持的一些基础类型。关于复合类型下次见。通过到目前的了解,可以发现,Go里还是有很多语法糖的,很多写法都和java这样的语言不同,似乎借鉴了很多像python之类的语言,尽量简单。有时间要去了解一下Go语言的设计哲学。