Go语言中有丰富的数据类型,除了基本的整型、浮点型、布尔型、字符串外,还有数组、切片、结构体、函数、map、通道(channel)等。

基本数据类型

整型

整型分为以下两个大类: 按长度分为:int8、int16、int32、int64 对应的无符号整型:uint8、uint16、uint32、uint64

其中,uint8就是我们熟知的byte型,int16对应C语言中的short型,int64对应C语言中的long型。

类型 描述
uint8 无符号 8位整型 (0 到 255)
uint16 无符号 16位整型 (0 到 65535)
uint32 无符号 32位整型 (0 到 4294967295)
uint64 无符号 64位整型 (0 到 18446744073709551615)
int8 有符号 8位整型 (-128 到 127)
int16 有符号 16位整型 (-32768 到 32767)
int32 有符号 32位整型 (-2147483648 到 2147483647)
int64 有符号 64位整型 (-9223372036854775808 到 9223372036854775807)
  • 特殊整型

    类型 描述
    uint 32位操作系统上就是uint32,64位操作系统上就是uint64
    int 32位操作系统上就是int32,64位操作系统上就是int64
    uintptr 无符号整型,用于存放一个指针

    注意: 在使用intuint类型时,不能假定它是32位或64位的整型,而是考虑intuint可能在不同平台上的差异。

    注意事项 获取对象的长度的内建len()函数返回的长度可以根据不同平台的字节长度进行变化。实际使用中,切片或 map 的元素数量等都可以用int来表示。在涉及到二进制传输、读写文件的结构描述时,为了保持文件的结构不会受到不同编译目标平台字节长度的影响,不要使用intuint

  • 进制

    不能直接声明二进制数

    十进制(%d)

    1
    2
    3
    4
    5
    6
    //十进制
    var i1 = 101
    fmt.Printf("%d\n", i1) //十进制输出
    fmt.Printf("%b\n", i1) //把十进制转换为二进制
    fmt.Printf("%o\n", i1) //把十进制转换为八进制
    fmt.Printf("%x\n", i1) //把十进制转换为十六进制

    八进制(%o)

    1
    2
    3
    //八进制
    i2 := 077
    fmt.Printf("%d\n", i2) //八进制转换为十进制

    十六进制(%x)

    1
    2
    3
    //十六进制
    i3 := 0x1234567
    fmt.Printf("%d\n", i3) //十六进制数转换为十进制数

    查看数据类型(%T)

    1
    2
    3
    //查看数据类型
    i4 := 1234
    fmt.Printf("%T\n", i4)

    定义指定的数据类型(int8(123))

    1
    2
    3
    4
    //定义指定的数据类型
    i5 := int8(8)
    fmt.Printf("%d\n", i5)
    fmt.Printf("%T\n", i5)

    浮点型

    Go语言支持两种浮点型数:float32float64。这两种浮点型数据格式遵循IEEE 754标准: float32 的浮点数的最大范围约为 3.4e38,可以使用常量定义:math.MaxFloat32float64 的浮点数的最大范围约为 1.8e308,可以使用一个常量定义:math.MaxFloat64

    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    f := math.MaxFloat32 // float最大值
    fmt.Println(f)
    fmt.Printf("%f", f) // 使用%f可以打印浮点型数值

    f1 := 1.23456 // Go语言中默认为float64
    fmt.Printf("%T\n", f1)

    f2 := float32(1.23456) // 显示声明为float64
    fmt.Printf("%T", f2)

    //float32和float64位的值都不能相互转化
    //f1 = f2
    //f2 = f1

    注意:float32和float64位的值都不能相互转化

    复数

    complex64和complex128

    1
    2
    3
    4
    5
    6
    //定义complex64的复数
    var c1 complex64 = 3 + 4i
    fmt.Printf("%T:%v\n", c1, c1)
    // 默认为complex128的复数
    var c2 = 3 + 4i
    fmt.Printf("%T:%v", c2, c2)

    复数有实部和虚部,complex64的实部和虚部为32位,complex128的实部和虚部为64位。

    布尔值

    Go语言中以bool类型进行声明布尔型数据,布尔型数据只有true(真)false(假)两个值。

    注意:

    1. 布尔类型变量的默认值为false
    2. Go 语言中不允许将整型强制转换为布尔型.
    3. 布尔型无法参与数值运算,也无法与其他类型进行转换。
    1
    2
    3
    b1 := true
    var b2 bool // bool类型的值默认为false
    fmt.Printf("%T:%v\n%T:%v", b1, b1, b2, b2)

    字符串

    G语言中的字符串以原生数据类型出现,就像使用其他的原生数据类型(int, bool, float32, float64等)一样。Go语言中的字符串内部实现使用UTF8编码。字符串使用(“”)进行包裹,可以在Go语言的源码中直接添加非ASCII码字符。字符使用(‘’)进行包裹。

    1
    2
    s1 := "hello go!"
    fmt.Println(s1)
  • 转义字符

    转义符 含义
    \r 回车符(返回行首)
    \n 换行符(直接跳到下一行的同列位置)
    \t 制表符
    \' 单引号
    \" 双引号
    \\ 反斜杠
  • 多行字符串

    多行字符使用反引号(``)包裹,被包裹的内容原样输出,不需进行转义。

    1
    2
    3
    4
    5
    6
    //多行字符
    s2 := `
    你好,世界?
    file:\a\b\c.txt
    `
    fmt.Printf(s2)
  • 字符串操作

    方法 介绍
    len(str) 求长度(Byte字节的数量)
    +或fmt.Sprintf 拼接字符串
    strings.Split 分割
    strings.contains 判断是否包含
    strings.HasPrefix,strings.HasSuffix 前缀/后缀判断
    strings.Index(),strings.LastIndex() 子串出现的位置
    strings.Join(a[]string, sep string) join操作
  • byte和rune类型

    组成每个字符串的元素叫做“字符”,可以通过遍历或者单个获取字符串元素获得字符。 字符用单引号(’)包裹起来,如:

    1
    2
    var a := '中'
    var b := 'x'

    Go语言的字符有两种:

    • 1、uint8类型,或者叫byte型,代表了ASCII码的一个字符

    • 2、rune类型,代表一个UTF8类型,实际类型是int32,处理中文,日文其他复合字时,需要用到rune类型。

      Go 使用了特殊的 rune 类型来处理 Unicode,让基于 Unicode 的文本处理更为方便,也可以使用 byte 型进行默认字符串处理,性能和扩展性都有照顾。

      1
      2
      3
      4
      5
      6
      7
      8
      9
      10
      11
      12
      // 遍历字符串
      func traversalString() {
      s := "hello沙河"
      for i := 0; i < len(s); i++ { //byte
      fmt.Printf("%v(%c) ", s[i], s[i])
      }
      fmt.Println()
      for _, r := range s { //rune
      fmt.Printf("%v(%c) ", r, r)
      }
      fmt.Println()
      }

      输出:

      1
      2
      104(h) 101(e) 108(l) 108(l) 111(o) 230(æ) 178(²) 153() 230(æ) 178(²) 179(³) 
      104(h) 101(e) 108(l) 108(l) 111(o) 27801(沙) 27827(河)

      因为UTF8编码下一个中文汉字由3~4个字节组成,所以我们不能简单的按照字节去遍历一个包含中文的字符串,否则就会出现上面输出中第一行的结果。

      字符串底层是一个byte数组,所以可以和[]byte类型相互转换。字符串是不能修改的 字符串是由byte字节组成,所以字符串的长度是byte字节的长度。 rune类型用来表示utf8字符,一个rune字符由一个或多个byte组成。

    • 修改字符串

      修改字符串要先将字符串转换为[]rune或byte[],修改完成后再转成string。无论哪种转换,都会重新分配内存,并赋复制字节数组。

      1
      2
      3
      4
      5
      6
      7
      8
      9
      10
      11
      12
      13
      14
      15
      16
      17
      //字符串修改
      func changeString() {
      s1 := "big"
      fmt.Println(s1)
      //强制类型转换
      bytes := []byte(s1)
      bytes[0] = 'p'
      s1 = string(bytes)
      fmt.Println(s1)

      s2 := "白萝卜"
      fmt.Println(s2)
      runes := []rune(s2)
      runes[0] = '红'
      s2 = string(runes)
      fmt.Println(s2)
      }
    • 类型转换

      Go语言中只有强制转换,没有隐式转换。并且转换时只能在两个类型之间支持相互转换时才能使用。

      1
      T(表达式)

      T表式要转换的类型。表达式包括变量,复杂式子、和函数返回值等。

      Example:

      1
      2
      3
      4
      5
      6
      7
      8
      //强制转换
      func sqrtDemo() {
      var a, b = 3, 4
      var c int
      //求第三边边长
      c = int(math.Sqrt(float64(a*a + b*b)))
      fmt.Println(c)
      }