wayou / wayou.github.io

https://wayou.github.io/
147 stars 12 forks source link

[golang]string & rune & byte #289

Open wayou opened 3 years ago

wayou commented 3 years ago

[golang]string & rune & byte

字符串并不由 rune 组成,而是由 byte 组成。同数组,slice 一样,可通过索引访问对应位置的元素,也能使用 slice 那样的截取语法。

func main() {
    var s string = "hello word!"
    var b byte = s[1]
    s2 := s[:5]
    s3 := s[6:]
    fmt.Println(b)  // 101
    fmt.Println(s2) // hello
    fmt.Println(s3) // word!
}

同数组和 slice, 可使用 len 获取字符串的长度。因为本质上字符串是 byte 组成的,所以,这里得到的是 byte 数,而不是真实的字符数。

func main() {
    s1 := "hello"
    s2 := "你好"
    fmt.Println(len(s1), len(s2)) // 5 6
}

也是由于字符串是 byte 为单位的缘故,如果字符串中存储的不是英文等一个字符占一个 byte 的情形时,最好不要使用 slice 操作字符串,因为得到的很可能不是一个完整的可见字符

字符串 & rune & bype 的互转

可通过类型转换操作将 rune 及 byte 转成字符串:

func main() {
    var a rune = 'x'
    var s string = string(a)
    var b byte = 'y'
    var s2 string = string(b)
    fmt.Println(s, s2)
}

反之亦然,

func main() {
    s := "hello"
    b := []byte(s)
    r := []rune(s)
    fmt.Println(b, r)
    // [104 101 108 108 111] [104 101 108 108 111]
}

不仅字符串,其实大部分情况 下,Go 中数据就是一串连续的 bytes。

注意:将数字转字符串时,结果是数字对应的字符编码所代表的字符,比如:

func main() {
    x := 65
    s := string(x)
    fmt.Println(s) // A
}

rune

和 byte 不同,rune 是字符为单位,这点在 for-range 时体现了出来:

func main() {
    s := "hello😵!"
    for i, v := range s {
        fmt.Println(i, v, string(v))
    }
}

// 输出结果:
// 0 104 h
// 1 101 e
// 2 108 l
// 3 108 l
// 4 111 o
// 5 128565 😵
// 9 33 !

以上。