Go指南2-基本类型

609 阅读4分钟

前言

Go的基本类型有:

  • int8, int16, int32, int64, int
  • uint8, uint16, uint32, uint64, uint
  • float32, float64
  • complex64, complex128
  • bool
  • byte
  • rune
  • string

整型

有符号整型

int8:表示 8 位有符号整型(00000000 ~ 11111111, 第一位是符号位)
大小:8 位
范围:-128~127

int16:表示 16 位有符号整型
大小:16 位
范围:-32768~32767

int32:表示 32 位有符号整型
大小:32 位
范围:-2147483648~2147483647

int64:表示 64 位有符号整型
大小:64 位
范围:-9223372036854775808~9223372036854775807

int:根据不同的底层平台自动选择 32 或 64 位整型。除非对整型的大小有特定的需求,否则你通常应该使用int表示整型。

无符号整型

uint8:表示 8 位无符号整型
大小:8 位
范围:0~255

uint16:表示 16 位无符号整型
大小:16 位
范围:0~65535

uint32:表示 32 位无符号整型
大小:32 位
范围:0~4294967295

// 之前遇到的一个坑:想判定时间戳是否符合规范,且习惯用uint32,忘记考虑uint32的范围
func uint32diff64() {
	a := uint32(math.Pow10(11))  // 1215752192
	b := uint64(math.Pow10(11))  // 100000000000
	fmt.Println(a, b)
}


uint64:表示 64 位无符号整型
大小:64 位
范围:0~18446744073709551615

uint:根据不同的底层平台,选择 32 或 64 位无符号整型。 在 32 位系统下是 32位 (0~4294967295),而在 64 位系统下是 64位 (0~18446744073709551615)。

如何查看字节数? 利用 unsafe.Sizeof

package main

import (
	"fmt"
	"unsafe"
)

func main()  {
	var a uint8 = 124
	var b int = 2147483649

	fmt.Println("size:", unsafe.Sizeof(a))  // 占1个字节
	fmt.Println("size:", unsafe.Sizeof(b))  // 我的机器是64位,所以是8字节
}

浮点型

float32:32 位浮点数,占4个字节
float64:64 位浮点数,占8个字节

精度问题:mp.weixin.qq.com/s/wq_zt8gQg…

复数类型

复数类型的实部和虚部类型需一致,比如complex64类型的实部和虚部都是 float32 类型;complex128类型的实部和虚部都是 float64 类型

布尔类型

由于Go是强类型语言,所以0和false,1和true并不对等(在Python中是相等的)

# python
>>> True == 1
True
>>> False == 0
True

byte 和 rune

由于97可以理解为一个数字,也可以理解为字符a(ASCII码),所以为了区分传递过来的到底是整型还是字符串(只是逻辑上的区分),诞生了byte和rune两种类型。

其中,byte是uint8 的别名,rune是int32的别名 20200213000457-2020-2-13-0-4-58.png

func runeLab() {
	var a uint8 = 97
	var b byte = 97
	fmt.Println(a == b)  // True, a 和 b 本质一样,但逻辑含义不同
	fmt.Println(a)
	fmt.Println(string(b)) // "a"
}

零值

如果一个变量没有赋予初始值,则会被赋予它们的零值,即默认值。

数值类型的零值为 0
布尔类型的零值为 false
字符串为的零值 ""(空字符串)
pointer, channel, func, interface, map, slice 类型的零值为nil

字符串类型

由于和其他语言相比,字符串在 Go 语言中有着自己特殊的实现,主要有以下几个特点。

  • 1.字符串是字节的集合,即[]byte。
  • 2.单引号和双引号代表的意义不同, 单引号是rune类型,双引号才是字符串类型。
  • 3.多行字符串可用反引号表示,但不支持转义
func stringLab() {
	name := "言淦"
	fmt.Println([]byte(name)) // 本质是字节数组 [232 168 128 230 183 166]

	// 多行字符串
	multiStr := `Hello
				 World!`
	fmt.Println(multiStr)
}

获取字符串长度

  • 使用 bytes.Count() 统计
  • 使用 strings.Count() 统计
  • 将字符串转换为 []rune 后调用 len 函数进行统计
  • 使用 utf8.RuneCountInString() 统计
str := "我是谁"
l1 := len([]rune(str))  // 3
l2 := bytes.Count([]byte(str), nil) - 1  // 3
l3 := strings.Count(str, "") - 1  // 3
l4 := utf8.RuneCountInString(str)  // 3

字符串的格式化

studygolang.com/articles/10…

类型转换

字符串和byte互转

func str2byte() {
	name := "言淦"

	nameBytes := []byte(name) // byte [232 168 128 230 183 166]
	nameString := string(nameBytes) // 言淦

	fmt.Println(nameBytes)
	fmt.Println(nameString)
}

字符串和int互转

整型转字符串类型主要有三种方法:

  • fmt.Sprintf:效率最低
  • strconv.Itoa:效率第二位,封装了FormatInt
  • strconv.FormatInt:效率最高

字符串转整型有两种办法:

  • strconv.Atoi
  • strconv.ParseInt
func str2int() {
	// int --> string
	var num int = 100
	str1 := fmt.Sprintf("%d", num)
	str2 := strconv.Itoa(num)
	str3 := strconv.FormatInt(int64(num), 10)
	fmt.Println(str1, str2, str3)

	// string --> int
	var str string = "100"
	num1, _ := strconv.Atoi(str)
	num2, _ := strconv.ParseInt(str, 10, 64)
	fmt.Println(reflect.TypeOf(num1))  // int
	fmt.Println(reflect.TypeOf(num2))  // int64
	fmt.Println(num1, num2)
}

参考

Golang数字转字符串