💜 想真正擅长编程? 从一门课程开始,100% 免费

《笔记》第十二篇 Go基本数据类型

第12讲 Go基本数据类型

本讲基于视频实际讲解内容整理


一、Go与Java数据类型对比

1.1 Java的基本类型

老师首先回顾了Java的基础类型特点:

  • Java中基础的 int 类型是完全不能自定义的,int的尺寸永远不变
  • Java是跨平台语言,原生基本类型的内存由 JVM统一规定,保证"一次编译,到处运行"
  • C/C++则不同,不同平台下基本类型大小可能变化
  • Java中有替代方案 byte 来替代 int 以减少内存占用

1.2 Go的数据类型优势

Go语言提供了更灵活的数值类型选择,可以针对不同场景选择不同大小的类型,从而写出高性能的代码。


二、整数类型

2.1 有符号整数(int)

类型 大小 范围
int8 1字节 -128 ~ 127
int16 2字节 -32768 ~ 32767
int32 4字节 -2147483648 ~ 2147483647
int64 8字节 更大范围

2.2 无符号整数(uint)

类型 大小 范围
uint8 1字节 0 ~ 255
uint16 2字节 0 ~ 65535
uint32 4字节 0 ~ 4294967295
uint64 8字节 更大范围

2.3 平台相关类型

int 和 uint 是与CPU平台相关的类型,不指定大小时:

  • 在不同的操作系统中大小不一样
  • 不同的编译器即使在相同硬件平台上也可能产生不同的大小

2.4 溢出演示

老师在视频中演示了类型溢出的效果:

Go
package main

import "fmt"

func main() {
    // uint8 范围 0~255,超出会溢出
    var u uint8 = 255
    fmt.Println(u)  // 255
    // u = u + 1    // 溢出后会变成 0

    // int8 范围 -128~127
    var a int8 = 127
    fmt.Println(a)  // 127
    // a = 128      // 编译报错:超出范围!

    // int8 赋值 200 会报错
    // var b int8 = 200  // constant 200 overflows int8

    // 改用 uint16 就可以了
    var c uint16 = 300
    fmt.Println(c)  // 300

    // 各种整数类型
    var d int32 = 100
    var e int64 = 200
    fmt.Println(d, e)
}

关键要点:使用数据类型时一定要注意范围限制,不要让它溢出。


三、浮点数类型

3.1 两种精度

类型 大小 精度
float32 4字节 单精度
float64 8字节 双精度

3.2 浮点数运算

Go
package main

import "fmt"

func main() {
    // 浮点数声明
    a := 20.0129999
    fmt.Println(a)

    // Go是强类型语言,不同类型不能直接混合运算
    // var b int = 10
    // var c float64 = 20.5
    // result := b + c  // 编译报错!类型不匹配

    // 浮点数的格式化输出
    // %g - 更紧凑的表示
    // %e - 科学计数法
}

3.3 强类型语言的严格性

老师特别强调:

"Go是强类型的语言,不同的数字不能直接混合运算。"

  • Go强制你写出健全的代码
  • 不同类型之间不能直接运算,需要显式类型转换
  • 未使用的变量也会直接报错(不仅仅是警告)
  • 老师提到 Rust语言在这方面更加严格

四、复数类型

4.1 complex64 和 complex128

Go
package main

import "fmt"

func main() {
    // 复数声明
    var c complex64 = 10 + 0i
    fmt.Println(c)

    // 使用 i 表示虚部
    var d = 0 + 10i
    fmt.Println(d)

    // 1 + 2i
    var e = 1 + 2i
    fmt.Println(e)  // (1+2i)
}

4.2 复数的规则

  • 一个浮点数字面量后面跟 i,它就是一个复数的虚部
  • 复数的实部默认为0
  • 常量算数规则下,复数可以加到另一个普通数值常量上

老师说明:复数类型目前用不上,先体验一下,后面用到再说。


五、布尔类型(bool)

Go
package main

import "fmt"

func main() {
    // 布尔类型使用 true 和 false
    var b bool = true
    fmt.Println(b)  // true

    // 比较运算
    a := 10
    fmt.Println(a == 10)  // true
    fmt.Println(a > 5)    // true

    // 不同类型不能直接比较
    // var c int = 10
    // var d int8 = 16
    // fmt.Println(c == d)  // 编译报错!类型不匹配

    // 相同类型可以比较
    var e int = 10
    var f int = 10
    fmt.Println(e == f)  // true
}

六、字符串类型(string)

6.1 基本概念

  • 字符串是一个不可改变的字节序列
  • 包括 byte(值的零)和 rune
  • 通常用来包含人类可读的文本
  • Go已经采用 UTF-8编码,可以直接使用中文

6.2 字符串操作

Go
package main

import "fmt"

func main() {
    // 直接使用中文(UTF-8编码)
    a := "我是中国人"
    fmt.Println(a)

    // 字符串长度(字节数)
    fmt.Println(len(a))

    // 通过下标访问字节
    fmt.Println(a[0])   // 输出字节值
    fmt.Println(a[1])
    fmt.Println(a[2])   // 中文字符的第一个字节值是 97...
}

6.3 ASCII编码

老师讲解了字符串中数字的来源:

  • ASCII 是一个标准编码
  • 用 7位二进制 表示字符
  • 所有英文字符都有对应的ASCII码值
  • 例如:'a' 的ASCII码是 97

七、指针与数据类型的结合

老师在本讲中还结合指针做了演示:

Go
package main

import "fmt"

func main() {
    a := 10
    fmt.Println(&a)         // 取内存地址

    b := &a                  // b 存储a的地址
    fmt.Println(b)           // 输出地址
    fmt.Println(*b == a)     // true,说明b确实指向a
}

八、本讲小结

知识点 要点
整数类型 int8/16/32/64(有符号)、uint8/16/32/64(无符号)
平台相关 int/uint 大小取决于CPU平台和编译器
溢出 超出类型范围会溢出或编译报错
浮点数 float32(单精度)、float64(双精度)
强类型 不同类型不能直接混合运算
复数 complex64/complex128,用 i 表示虚部
布尔 true/false,不同类型不能直接比较
字符串 不可变字节序列,UTF-8编码,可直接用中文
ASCII 7位二进制表示字符的标准编码
指针 &取地址,*解引用

九、课后练习

  1. 声明 int8、uint8、int32、uint64 类型的变量,分别赋值并打印
  2. 尝试给 int8 赋值 200,观察编译报错信息
  3. 声明一个 float64 变量,尝试与 int 类型变量直接相加,观察报错
  4. 声明一个包含中文的字符串,使用 len() 和下标访问观察输出
  5. 使用 & 和 * 操作符,验证指针指向的值与原变量是否相等