Go基础之国际化字符"rune"

  • 基本的概念,什么是Unicode,什么是UTF-8,什么是UTF-16。

Unicode,UTF-8,UTF-16完整的说明请参考Wiki(UnicodeUTF-8UTF-16)。用比较简单的话来说就是,Unicode定义了所有可以用来表示字符的数值集合(称之为Code Point)。UTF-8和UTF-16等UTF标准定义了这些数值和字符的映射关系。

在UTF8编码中,英文字符占用一个字节;绝大多数汉字占用三个字节,个别汉字占用四个字节。

  • go中的"rune"类似与Java或其他语言中的"char",但"rune"占4个字节,相当于int32的别名,可以很好的支持中文字符等国际化字符,而"char"只占2个字节,不能很好的支持汉字等字符

package main

import (
    "fmt"
    "unicode/utf8"
)

func main() {
    s := "Yes我是中国人!"
    
    fmt.Println(len(s))   //结果:21  UTF-8编码  一个英文字母和一个标点各占一个字符,一个汉字占三个字符
    
    fmt.Printf("%x \n", s)  //结果:596573e68891e698afe4b8ade59bbde4babaefbc81 
    fmt.Println([]byte(s))  //结果:[89 101 115 230 136 145 230 152 175 228 184 173 229 155 189 228 186 186 239 188 129]
    fmt.Printf("%d\n", []byte(s)) //结果:[89 101 115 230 136 145 230 152 175 228 184 173 229 155 189 228 186 186 239 188 129]
    fmt.Printf("%x\n", []byte(s))  //结果:596573e68891e698afe4b8ade59bbde4babaefbc81 
    fmt.Printf("%s\n", []byte(s))  //结果:Yes我是中国人!
    
    for _, v := range []byte(s){
        fmt.Printf("%x ", v)  //结果:59 65 73 e6 88 91 e6 98 af e4 b8 ad e5 9b bd e4 ba ba ef bc 81  这里可以看到UTF-8编码
    }
    fmt.Println()
    
    for i, ch := range s {    //对一个string遍历,获得的每个字符都是一个rune
        fmt.Printf("(%d, %x) ", i, ch)  
        //结果:(0, 59) (1, 65) (2, 73) (3, 6211) (6, 662f) (9, 4e2d) (12, 56fd) (15, 4eba) (18, ff01) 
        //这里的 ch 其实就是一个rune      输出长度为9, 英文字母,汉字,标点 各为一个rune
        //rune 是4字节的,这里只显示了后两个字节 且由原来的UTF-8转为了Unicode编码
        //注意 输出的"i"不是连续的 这里的"i"是每个rune起始字节在整个字节数组中的索引值,rune 的码点

    }
    fmt.Println()
    
    fmt.Println(utf8.RuneCountInString(s))  //结果:9 想获得一个string(包含汉字)的长度 可以用 utf8.RuneCountInString(s)
    
    bytes := []byte(s)
    for len(bytes)>0 {
        ch, size := utf8.DecodeRune(bytes)
        bytes = bytes[size:]
        fmt.Printf("%c ", ch)  //结果: Y e s 我 是 中 国 人 ! 
    }
    fmt.Println()
    
    //实际中,往往是想获得string中每个字符的索引和内容 可以将string转为[]rune
    for i, ch := range []rune(s) {
        fmt.Printf("(%d,%c) ", i, ch)  //结果:(0,Y) (1,e) (2,s) (3,我) (4,是) (5,中) (6,国) (7,人) (8,!) 
    }
}

  • 总结: ​​​​​​​​​​​​​​
  1. 直接用range 遍历一个带有汉字的string,得到的索引是 每个汉字开头字节的索引,以及汉字的unicode编码
  2. 可以先将string转为[]rune 再进行遍历,这样可以获得汉字的索引及汉字
  3. 对string 使用len(s) 获得的是string的字节长度; 而可以对string使用utf8.RuneCountInString(s)获得string中的rune长度
  • string的一些其他常见操作 

"strings"包: 

  1. ​​​​​​​Fields, Split, Join
  2. Contains, Index
  3. ToLower, ToUpper
  4. Trim, TrimRight, TrimLeft
  • 1
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值