目录
本文列举关于字符串最常用的几个操作,都会举例说明
- 字符串长度
- 查找
- 替换
- 分割
- 合并
- 前缀或后缀
- 截取
- 删除
- 插入
- 编码转换
- 转换数值类型
- 大小写转换
- Trim操作
- ASCII 转换
- 字符串重复几次
- 字符或子串在字符串中首次出现的位置或最后一次出现的位置
字符串相关操作需要导入包strings
字符串长度
len()
1 | func strLength() { |
查找
func Contains(s, substr string) bool
子串substr在s中,返回truefunc ContainsAny(s, chars string) bool
chars中任何一个字符在s中,返回truefunc ContainsRune(s string, r rune) bool
Unicode代码点r在s中,返回truefunc Count(s, sep string) int
sep 在s中重复出现的次数(不计算重叠)func Index(s, sep string)
int 在字符串s中查找sep所在的位置, 找不到返回-1
在Go中,查找子串出现次数即字符串模式匹配,实现的是Rabin-Karp算法。
另外,Count 是计算子串在字符串中出现的无重叠的次数
1 | func existSubStringOrChar() { |
结果
1 | true true |
替换
strings.Replace(s, old, new, n)
s
需要替换的字符串 old
需要被替换掉的某个子串 new
替换的值n
n<0
全部替换 n==0
不替换 n>0
全部替换 如果n
的下标匹配上old值,则只替换当前下标的字符,如果不是,则全部替换
1 | func strReplace() { |
结果1
cvbcdefgvbc cabcdefgabc cvbcdefgabc cvbcdefgvbc
分割
Fields 和 FieldsFunc
- Fields 按空格切割
- FieldsFunc 按照自己指定的方式切割
实际上,Fields 函数就是调用 FieldsFunc 实现的:1
2
3func Fields(s string) []string {
return FieldsFunc(s, unicode.IsSpace)
}
1 | func strCut() { |
结果1
2[abc bde efg] [abc bde efg]
[ab*cd*ef]
Split 和 SplitAfter、 SplitN 和 SplitAfterN
1 | func Split(s, sep string) []string { return genSplit(s, sep, 0, -1) } |
它们都调用了 genSplit 函数。
这四个函数都是通过 sep 进行分割,返回[]string。如果 sep 为空,相当于分成一个个的 UTF-8 字符,如 Split(“abc”,””),得到的是[a b c]。
功能区分:after 会保留分隔符
1 | fmt.Printf("%q\n", strings.Split("foo,bar,baz", ",")) |
输出:1
2["foo" "bar" "baz"]
["foo," "bar," "baz"]
N的区别
N
用来控制分割的个数
当 n < 0 时,返回所有的子字符串;当 n == 0 时,返回的结果是 nil;当 n > 0 时,表示返回的 slice 中最多只有 n 个元素,其中,最后一个元素不会分割
fmt.Printf("%q\n", strings.SplitN("foo,bar,baz", ",", 2))
输出:["foo" "bar,baz"]
另外看一下官方文档提供的例子,注意一下输出结果:1
2
3
4fmt.Printf("%q\n", strings.Split("a,b,c", ","))
fmt.Printf("%q\n", strings.Split("a man a plan a canal panama", "a "))
fmt.Printf("%q\n", strings.Split(" xyz ", ""))
fmt.Printf("%q\n", strings.Split("", "Bernardo O'Higgins"))
输出:1
2
3
4["a" "b" "c"]
["" "man " "plan " "canal panama"]
[" " "x" "y" "z" " "]
[""]
split总结
关于字符串的分割,最常用的就是Split
,其他几乎用不到
合并
将字符串数组(或slice)连接起来可以通过 Join 实现
func Join(a []string, sep string) string
1 | func strJoin() { |
输出:1
2
3[a b c]
a-b-c
abc
前缀或后缀
1 | func presuf() { |
输出:true true
截取
1 | func subString() { |
输出:1
abc中
删除
strings 包中没有提供删除的方法,只能自己实现
1 | func deleteStrWithRange(s string, start int, end int) string { |
1 | var sss = deleteStrWithRange("012345678", 1, 3) |
输出:0345678
插入
go strings 包没有插入方法,只能将字符串转化为切片,然后插入元素,再转为string
编码转换
字符串转换需要用到 strconv
- Append 函数表示将给定的类型(如bool, int等)转换为字符串后, 添加在现有的字节数组中[]byte
- Format 函数将给定的类型变量转换为string返回
- Parse 函数将字符串转换为其他类型
unicode 与 中文 互转
1 | func chinaeseToUnicode() { |
输出1
2
3"\u4e2d\u6587"
\u4e2d\u6587
中文
转码与解码
需要导入包 net/url
1 | func encodeAndDecode() { |
输出1
2https%3A%2F%2Fwww.baidu.com%2F%E7%94%9F%E6%B4%BB
https://www.baidu.com/生活
转换数值类型
1 | func strToValue() { |
输出1
2
3123 string
45678 int
123.45678 float64
大小写转换
1 | // 给定字符串转换为英文标题的首字母大写的格式(不能正确处理unicode标点) |
1 | fmt.Println(strings.Title("her royal highness")) // Her Royal Highness |
Trim操作
bytes提供了有Compare、Count、Equal、Index、Join、Split、Replace等直接针对[]byte类型的函数。还有一个重要的Buffer类,将[]byte类型当作一个缓冲区,提供了对这个缓冲区便捷的操作:读、写、和string/rune之间的转换、迭代等函数。
在bytes库中,有Trim系列的函数,它的功能是对[]byte类型做裁剪,去除不需要的部分。
func Trim(s string, cutset string) string
去除两边自定义字符func TrimFunc(s string, f func(rune) bool) string
自定义清除func TrimLeft(s string, cutset string) string
清除左边func TrimPrefix(s, prefix string) string
删除前缀
1 | func strtrim() { |
输出:
1 | ads!/ ;' jha asdfhj |
ASCII 转换
1 | func strASCII() { |
输出
1 | 'a' convert to ASCII 97 |
字符串重复几次
func Repeat(s string, count int) string
1 | func strRepeatCount() { |
输出
aa
字符或子串在字符串中首次出现的位置或最后一次出现的位置
4个查找第一次出现的位置
// 在 s 中查找 sep 的第一次出现,返回第一次出现的索引func Index(s, sep string) int
// chars中任何一个Unicode代码点在s中首次出现的位置func IndexAny(s, chars string) int
// 查找字符 c 在 s 中第一次出现的位置,其中 c 满足 f(c) 返回 truefunc IndexFunc(s string, f func(rune) bool) int
// Unicode 代码点 r 在 s 中第一次出现的位置func IndexRune(s string, r rune) int
一般用indexAny
3个查找最后一次出现的位置
func LastIndex(s, sep string) int
func LastIndexAny(s, chars string) int
func LastIndexFunc(s string, f func(rune) bool) int
一般用LastIndexAny
就行