文章目录
一、字符串的处理:
1. strings包:
从文件中将数据读取出来后,很多情况下并不是将数据打印出来, 而是要做相对应的处理. 例如: 去掉空格等一些特殊符号, 对一些内容进行替换等;
这里涉及到对一些字符串的处理, 需要借助于包"strings"
- 常用的字符串处理函数:
- Contains;
- Join:
- Index;
- Repeat;
- Replace
- Split;
- Trim;
- Fields;
2. Contains是否包含:
语法:
func Contains(s, substr string) bool
功能:字符串s中是否包含substr,返回bool值
import (
"fmt"
"strings"
)
func main() {
str1 := "hello world"
str2 := "h"
// Contains(被查找的字符串, 查找的字符串) 返回值: bool
// 一般用于模糊查找
b := strings.Contains(str1, str2)
fmt.Println(b) // true
}
3. Join: 字符串连接
语法:
func Join(a []string, sep string) string
功能:字符串链接,把slicea通过sep链接起来
func main() {
// 字符串切片
slice := []string{"123", "abc", "456"}
// Join(切片, "分隔符")
str1 := strings.Join(slice, ",")
fmt.Println(str1) // 123,abc,456
}
4. Index查找索引
语法:
func Index(s, substr string) int
功能:在字符串s中查找sep所在的位置,返回位置值,找不到返回-1
func main() {
str1 := "hello world"
str2 := "g"
str3 := "h"
// Index(要查找的字符串, 查找内容): 查找一个字符串在另一个字符串中第一次出现的位置, 返回值: int下标; -1表示找不到
i1 := strings.Index(str1, str2)
fmt.Println(i1) // -1
i2 := strings.Index(str1, str3)
fmt.Println(i2) // 0
}
5. Repeat: 重复
语法:
func Repeat(s string, count int) string
功能:重复s字符串count次,最后返回重复的字符串
func main() {
str := "hello world..."
// 将一个字符串重复n次
str1 := strings.Repeat(str, 5)
fmt.Println(str1) // hello world...hello world...hello world...hello world...hello world...
}
6. Replace:替换:
语法:
func Replace(s, old, new string, n int) string
功能:在s字符串中,把old字符串替换为new字符串,n表示替换的次数,小于0表示全部替换
func main() {
str := "一些敏感的词汇的敏感"
// 字符串替换, 屏蔽敏感词汇
str1 := strings.Replace(str, "敏感", "**", 1)
fmt.Println(str1) // 一些**的词汇的敏感
// 如果替换次数小于0, 则表示全部替换
str2 := strings.Replace(str, "敏感", "**", -1)
fmt.Println(str2) // 一些**的词汇的**
}
7. Split: 分割
语法:
func Split(s, sep string) []string
功能:把s字符串按照sep分割,返回slice
func main() {
str1 := "130-188-1999"
// 切割字符串
slice := strings.Split(str1, "-")
fmt.Println(slice) // [130 188 1999]
}
8. Trim: 去除指定的字符串
语法:
func Trim(s string, cutset string) string
功能:在s字符串的头部和尾部去除cutset指定的字符串
func main() {
str := "===are===U===OK==="
// Trim: 去掉字符串指定的首位内容
str1 := strings.Trim(str, "=")
fmt.Println(str1) // are===U===OK
}
9. Fields: 去除空格
语法:
func Fields(s string) []string
功能:去除s字符串的空格符,并且按照空格分割返回slice
func main() {
str := " are U ok "
// 去掉头尾的空格, 一般用于统计单词个数
slice := strings.Fields(str)
fmt.Println(slice) // [are U ok]
}
二、字符串的类型转换:
1. strconv包:
GO语言也提供了字符串与其它类型之间相互转换的函数; 相应的字符串转换函数都在"strconv"包
- 字符串转换:
- Format;
- Parse;
- Append;
2. 字符串转字符切片:
func main() {
str := "hello world"
// 将字符串转成字符切片 => 强制类型转换
slice := []byte(str)
fmt.Println(slice) // [104 101 108 108 111 32 119 111 114 108 100]
}
3. Format: 把其他类型的转换为字符串
Format 系列函数把其他类型的转换为字符串
func main() {
// 字符串切片
slice := []byte{'h', 'e', 'l', 'l', 'o', 97}
fmt.Println(slice) // [104 101 108 108 111 97]
fmt.Println(string(slice)) // helloa
// 将其他类型转换成字符串
b := false
str1 := strconv.FormatBool(b)
fmt.Println(str1) // false
fmt.Printf("%T\n", str1) // string
str2 := strconv.FormatInt(140, 16) // 第二个参数是要转化的进制(2, 8, 10, 16)
fmt.Println(str2) // 8c
fmt.Printf("%T\n", str2) // string
str3 := strconv.FormatFloat(3.141592, 'f', 4, 64)
fmt.Println(str3) // 3.1416
fmt.Printf("%T\n", str3) // string
str4 := strconv.Itoa(123)
fmt.Println(str4) // 123
}
3. Parse: 把字符串转换为其他类型:
Parse 系列函数把字符串转换为其他类型
func main() {
// 将字符串转成其他类型
b1, err1 := strconv.ParseBool("true")
fmt.Println(b1, err1) // true <nil>
fmt.Printf("%T\n", b1) // bool
// 转换失败 返回false
b2, err2 := strconv.ParseBool("truee")
fmt.Println(b2, err2) // false strconv.ParseBool: parsing "truee": invalid syntax
fmt.Printf("%T\n", b2) // bool
v1, err3 := strconv.ParseInt("abc", 16, 64)
fmt.Println(v1, err3) // 2748 <nil>
fmt.Printf("%T\n", v1) // int64
v2, err4 := strconv.ParseFloat("3.14159", 64)
fmt.Println(v2, err4) // 3.14159 <nil>
fmt.Printf("%T\n", v2) // float64
}
4. Append:
Append 系列函数将整数等转换为字符串后,添加到现有的字节数组中
func main() {
// 将其他类型转成字符串, 并且添加到字符切片里
slice := make([]byte, 0, 1024)
slice = strconv.AppendBool(slice, false)
slice = strconv.AppendInt(slice, 123, 2)
slice = strconv.AppendFloat(slice, 3.14159, 'f', 4, 64)
slice = strconv.AppendQuote(slice, "hello")
fmt.Println(slice, string(slice))
// [102 97 108 115 101 49 49 49 49 48 49 49 51 46 49 52 49 54 34 104 101 108 108 111 34] false11110113.1416"hello"
}
三、文件操作:
1. 新建文件:
将数据存储到文件之前, 先要创建文件. GO语言中提供了一个Create()函数专门创建文件.
该函数在创建文件时, 首先会判断要创建的文件是否存在, 如果不存在, 则创建, 如果存在, 会先将文件中已有的数据清空;
同时, 当文件创建成功后, 该文件会默认的打开, 所以不用在执行打开操作, 可以直接向该文件中写入数据;
- 创建文件的步骤:
- 导入"os"包, 创建文件, 读写文件的函数都在该包;
- 指定创建的文件存放路径以及文件名;
- 执行Create()函数, 进行文件创建;
- 关闭文件;
package main
import (
"fmt"
"os"
)
func main() {
// 返回值 => 文件指针 和 错误信息
fp, err := os.Create("./a.txt")
if err != nil {
//文件创建失败
/*
1.路径不存在
2.文件权限
3.程序打开文件上限
*/
fmt.Println("文件创建失败")
return
}
// todo: 读写文件
//关闭文件
//如果打开文件不关闭 造成内存的浪费 程序打开文件的上限
//fp.Close()
defer fp.Close()
}
2. 写入文件:
文件打开以后, 可以向文件中写数据, 可以使用WriteString()方法
package main
import (
"fmt"
"os"
)
func main() {
//\反斜杠 转义字符
//在写路径时可以使用/正斜杠代替\反斜杠
fp, err := os.Create("./a.txt")
if err != nil {
fmt.Println("文件创建失败")
return
}
// TODO: 写文件
// \n不会换行 原因 在windows文本文件中换行\r\n 回车 在linux中换行\n
fp.WriteString("hello world...\r\n")
fp.WriteString("123456789...\r\n")
defer fp.Close()
}
func main() {
fp, err := os.Create("./a.txt")
if err != nil {
fmt.Println("文件创建失败")
return
}
// TODO: 写文件
// slice := []byte{'h', 'e', 'l', 'l', 'o'}
// count, err := fp.Write(slice) // 5
count, err := fp.Write([]byte("好好学习, 天天向上")) // 26
if err != nil {
fmt.Println("写入文件失败")
return
} else {
fmt.Println(count)
}
defer fp.Close()
}
func main() {
fp, err := os.Create("./a.txt")
if err != nil {
fmt.Println("文件创建失败")
return
}
// TODO: 写文件
// 获取光标流位置
// 获取文件起始位置到结尾有多少字符
count, _ := fp.Seek(0, os.SEEK_END) // os.SEEK_END: 后续版本会取消
fmt.Println(count)
count1, _ := fp.Seek(0, io.SeekEnd)
fmt.Println(count1) // 0
// 按照指定位置写入
// func (f *File) WriteAt(b []byte, off int64) (n int, err error)
fp.WriteAt([]byte("hello world"), count1)
fp.WriteAt([]byte("哈"), 0) // 内容被覆盖了
fp.WriteAt([]byte("真香"), 19)
defer fp.Close()
}
3. 打开文件:
// os.Open() 只支持读操作, 不能进行写入操作
fp, err := os.Open("./a.txt")
func OpenFile(name string, flag int, perm FileMode) (*File, error)
说明:
- OpenFile( )这个函数有三个参数,第一个参数表示打开文件的路径,第二个参数表示模式,常见的模式有:
- O_RDONLY: 只读模式;
- O_WRONLY: 只写模式;
- O_RDWR: 可读可写模式;
- O_APPEND: 追加模式;
- 第三个参数, 表示权限, 取值范围(0-7)表示如下:
值 | 说明 |
---|---|
0 | 没有任何权限 |
1 | 执行权限(如果是可执行文件, 是可以运行的) |
2 | 写权限 |
3 | 写权限与执行权限 |
4 | 读权限 |
5 | 读权限与执行权限 |
6 | 读权限与写权限 |
7 | 读权限, 写权限, 执行权限 |
func main() {
// 打开存在的文件
// os.Open() 只支持读操作
// fp, err := os.Open("./a.txt")
// func OpenFile(name string, flag int, perm FileMode) (*File, error)
fp, err := os.OpenFile("./a.txt", os.O_RDWR, 6)
if err != nil {
fmt.Println("打开文件失败...")
return
}
// fp.WriteString("好好学习\r\n")
fp.WriteAt([]byte("hahahah"), 30)
defer fp.Close()
}
4. 读取文件内容:
Read 读取文件
如果文件已经存在, 并且也已经有数据了, 那么可以直接读取该文件中的内容;
读取文件的基本流程如下:
- 打开要读取的文件;
- 对文件进行读取;
- 关闭文件;
package main
import (
"fmt"
"io"
"os"
)
func main() {
//打开文件
fp, err := os.Open("D:/a.txt")
if err != nil {
fmt.Println("err=", err)
return
}
buf := make([]byte, 1024*2) //2k大小
//n代表从文件读取内容的长度
n, err1 := fp.Read(buf)
// io.EOF: 指文件的末尾
if err1 != nil && err1 != io.EOF {
fmt.Println("err1=", err1)
return
}
fmt.Println("buf=", string(buf[:n]))
//关闭文件
defer fp.Close()
}
按行读取:
方式一:
package main
import (
"bufio"
"fmt"
"io"
"os"
)
func main() {
fp, err := os.Open("./a.txt")
if err != nil {
fmt.Println("err=", err)
return
}
// 创建缓冲区
r := bufio.NewReader(fp)
// 行读取, 截取的标志 '\n'
slice, _ := r.ReadBytes('\n')
fmt.Println(string(slice))
slice, _ = r.ReadBytes('\n')
fmt.Println(string(slice))
for {
// 遇到\n就结束读取, 但是\n也需要读取
buf, err1 := r.ReadBytes('\n')
if err1 != nil || err1 == io.EOF {
fmt.Println("error = ", err1)
break
}
fmt.Println(string(buf))
}
//关闭文件
defer fp.Close()
}
方式二: 直接读取字符串
func main() {
fp, err := os.Open("./a.txt")
if err != nil {
fmt.Println("err=", err)
return
}
// 创建缓冲区
r := bufio.NewReader(fp)
// 行读取, 截取的标志 '\n'
slice, _ := r.ReadBytes('\n')
fmt.Println(string(slice))
slice, _ = r.ReadBytes('\n')
fmt.Println(string(slice))
for {
str, err1 := r.ReadString('\n')
if err1 != nil && err1 == io.EOF {
fmt.Println("error = ", err1)
break
}
fmt.Println(str)
}
//关闭文件
defer fp.Close()
}
5. 文件操作案例:
文件拷贝,将已有的文件复制一份,同时重新命名。
基本的思路:
- 让用户输入要拷贝的文件的名称(源文件)以及目的文件的名称;
- 创建目的文件;
- 打开源文件,并且读取该文件中的内容;
- 将从源文件中读取的内容写到目的文件中;
package main
import (
"fmt"
"io"
"os"
)
func main() {
var srcFilename string
var dstFilename string
fmt.Println("请输入原文件名称:")
fmt.Scan(&srcFilename)
fmt.Println("请输入目的文件名称:")
fmt.Scan(&dstFilename)
// 打开文件
fp, err := os.Open(srcFilename)
fd, err1 := os.Create(dstFilename)
if err != nil || err1 != nil {
fmt.Println("打开文件失败...")
return
}
//核心处理,从源文件读取内容,往目的文件写,读多少写多少
buf := make([]byte, 4*1024) //4k大小临时缓冲区
for {
n, err := fp.Read(buf) //从源文件读取内容,每次读取一部分
if err != nil || err == io.EOF { //文件读取完毕
break
}
//往目的文件写,读多少写多少
fd.Write(buf[:n])
}
// 关闭文件
defer fp.Close()
defer fd.Close()
}