【Hello Go】Go语言文本文件处理

news2024/11/15 23:39:41

文本文件处理

    • 字符串处理
      • 字符串操作
        • Contains
        • Join
        • index
        • repeat
        • Replace
        • Split
        • Trim
        • Fields
      • 字符串转换
        • Append
        • Format
        • Parse
    • 正则表达式
    • Json处理
      • 编码Json
        • 通过结构体生产Json
        • 通过map生产json
      • 解码Json
        • 解析到结构体
        • 解析到interface
    • 文件操作
      • 相关api介绍
        • 建立和打开文件
        • 关闭文件
        • 写文件
        • 读文件
        • 删除文件
      • 示例代码
        • 写文件
        • 读文件
        • 拷贝文件

字符串处理

字符串在开发的过程中经常用到 比如在用户的输入或者是数据库的读取操作中

我们经常需要对于字符串进行分割 链接 旋转等操作 我们可以通过Go语言标准库中的strings 和 strconv 两个包中的函数进行相应的操作

字符串操作

下面的函数来自于strings包 这里只介绍一些常用的函数 更加详细的介绍请参考Go语言的官方文档

Contains

函数原型如下

func Contains(s, substr string) bool

功能: 字符串s中是否包含substr 返回一个bool值 如果存在返回true 如果不存在返回false

值得注意的一点是空串在任意字符串中都存在

Join

函数原型如下

func Join(a []string, sep string) string

功能: 将切片a中的所有string通过sep链接起来 最后返回我们一个链接完毕的string

演示代码和效果如下

a := [] string{"foo" , "bar" , "baz"}
fmt.Println(strings.Join(s, ", "))
// 最后输出结果是 foo,bar,baz
index

函数原型如下

func Index(s, sep string) int

功能: 在字符串s中寻找sep的位置 找到返回位置值 找不到返回-1

	fmt.Println(strings.Index("chicken", "ken")) // 4
	fmt.Println(strings.Index("chicken", "dmr")) // -1
repeat

函数原型如下

func Repeat(s string, count int) string

功能:重复字符串s n次 并且返回重复后的字符串

代码示例如下

	fmt.Println("ba" + strings.Repeat("na", 2)) // banana
Replace

函数原型如下

func Replace(s, old, new string, n int) string

功能:把s字符串中old字符串替换为new字符串 n表示替换的次数 如果n小于0 则表示全部替换

	var s string = "oink oink oink"

	fmt.Println(strings.Replace(s, "k", "ky", 2))     // oinky  oinky  oink
	fmt.Println(strings.Replace(s, "oink", "oi", -1)) // oi  oi  oi
Split

函数原型如下

func Split(s, sep string) []string

功能: 把s字符串按照sep切割 最后返回一个切片

	fmt.Printf("%q\n", strings.Split("hello aa dasdasd dasdax3w", " ")) // ["hello" "aa" "dasdasd" "dasdax3w"]
	fmt.Printf("%q", strings.Split(" xyz ", "")) // [" " "x" "y" "z" " "]    
Trim

函数原型如下

func Trim(s string, cutset string) string

功能: 在s字符串的头部和尾部去除cutset字符串

	fmt.Println(strings.Trim("!!!    hello world @!!!!!!", " !@"))  // hello world
Fields

函数原型如下

func Fields(s string) []string

功能:去除s字符串的空格符,并且按照空格分割返回切片

func main() {
	fmt.Printf("%q", strings.Fields("str     abc     adw"))  // str abc adw
}

字符串转换

字符串转换函数在包 strconv 中 如下 我们也只是列出一些常用的函数

Append

append系列函数将各种类型转化为字符串之后 添加到现有的字符数组中

下面是示例代码

	str := make([]byte, 0, 100) // 创建一个长度为0的byte切片 预留长度大小为100

	str = strconv.AppendInt(str, 1234, 10) // 以10进制的方式往后添加1234
	str = strconv.AppendBool(str, false)
	str = strconv.AppendQuote(str, "hello world")
	str = strconv.AppendQuoteRune(str, '单')
	fmt.Println(string(str)) // 最后结果是1234false"hello world"'单'
Format

format系列函数将其他类型转化为字符串

代码演示如下

	a := strconv.FormatInt(1234, 10) // 将1234 以10进制的方式转化为字符串
	b := strconv.FormatBool(false)   // 讲false转化为字符串
	c := strconv.Itoa(1022)

	fmt.Println(a, b, c) // 1234 false 1022
Parse

parse系列函数将字符串转化为其他类型 但是转化的过程中有可能会失败 所以说我们要用一个err来接受看看是否转化失败 如果转化失败了 我们可以使用一个函数将其打印出来

func checkError(e error) {
	if (e != nil) {
		fmt.Println(e)
	}
}

func main() { 
	a , err := strconv.ParseInt("1234" , 10 , 64) // 将字符串1234 以10进制的方式转化为64位大小的int类型数据1234
	checkError(err)  
	fmt.Println(a)
}

正则表达式

正则表达式是一个较为庞大的内容 以后会单独开一篇博客来解释 此处就不过多赘述

Json处理

JSON是一种比XML更加轻量级的数据交换格式 在易于人们阅读和编写的同时也易于程序的编译和运行 尽管JSON是JavaScript的一个子集 但是json采用完全独立于编程语言的文本格式 并且表现为 键值对集合的文本描述形式 (类似于字典结构 ) 这使他成为一个跨平台 跨语言的数据交换语言

原来的信息如下

char name = "小明";
int age = 18;
float score[3] = {88.5, 99, 58};

转变为json存储之后如下

   {
        "姓名" : "小明",
        "年龄" : 18,
        "成绩" : [88.5, 99, 58]
   }

json存储实际上是将原来的数据变成了一个字符串 (也就是说上面的代码实际上就是一个字符串)

json 数据类型:对象,数组,字符串,数字 介绍如下

  • 对象:使用花括号 {} 括起来的表示一个对象。
  • 字符串:使用常规双引号 “” 括起来的表示一个字符串
  • 数字:包括整形和浮点型,直接使用。
  • 数组:使用中括号 [] 括起来的表示一个数组。

也就是说 如果我们有多组同类型的数据 我们可以使用数组组织起来

代码表示如下

[
   {
        "姓名" : "小明",
        "年龄" : 18,
        "成绩" : [88.5, 99, 58]
   },
   {
        "姓名" : "小黑",
        "年龄" : 18,
        "成绩" : [88.5, 99, 58]
   }
]

编码Json

通过结构体生产Json

使用json.Marshal()函数可以对一组数据进行json格式的编码 函数原型如下

func Marshal(v interface{}) ([]byte, error)

还有一个格式化输出

func MarshalIndent(v interface{}, prefix, indent string) ([]byte, error

示例代码如下

	t1 := IT{"itcast", []string{"Go", "C++"}, true, 666.66}

	// 下面生成一段json格式的文本
	b, err := json.Marshal(t1)
	// 如果成功 则err将会是空 b将会是一段json格式的文本  // {"Company":"itcast","Subjects":["Go","C++"],"IsOK":true,"Price":666.66}
	if err == nil {
		fmt.Println(string(b))
	} else {
		fmt.Println("error!!!!")
		fmt.Println(err)
	}

json.MarshalIndent 函数是 Go 语言中用于将数据结构转换为带有缩进格式的 JSON 字符串的函数。它提供了更易读的输出格式,便于阅读和调试。

func MarshalIndent(v interface{}, prefix, indent string) ([]byte, error)

这里主要介绍下prefix 和 indent参数

  • prefix 每行的前缀 如果我们将其赋值为 “hello” 那么以后每一行都会先打印一个hello
  • indent 表示缩进的大小 我们一般使用空字符串来进行缩进

下面是缩进后的格式

在这里插入图片描述

struct tag

我们可以看到上面的输出字段首字母都是大写的 那如果我们想要首字母小写怎么办呢 将结构体中的标识符修改为小写嘛

可是当我们将结构体中的标识符修改为小写之后我们发现json 不输出该字段

所以说我们写Json的时候需要注意 只有当导出字段的首字母是大写才会输出 如果我们修改字段为小写 就会发现该字段不会输出了

所以说我们必须要定义struct tag来实现

在Go语言中 结构体字段可以通过 tag 来进行注释和元数据的添加 它位于字段的后方 并且被反引号包围

我们的定义struct tag的时候需要注意的几点是

  • 字段的tag是"-",那么这个字段不会输出到JSON
  • tag中带有自定义名称,那么这个自定义名称会出现在JSON的字段名中
  • tag中如果带有"omitempty"选项,那么如果该字段值为空,就不会输出到JSON串中
  • 如果字段类型是bool, string, int, int64等,而tag中带有",string"选项,那么这个字段在输出到JSON的时候会把该字段对应的值转换成JSON字符串
type IT struct {
	Company  string   `json:"-"`        // 这里表示company不会出现在Json中
	Subjects []string `json:"subjects"` // 这里对于Subjiects重新命名了 所以说在最后会显示subjects
	IsOK     bool     `json:",string"`  // 先转化为字符串再输出
	Price    float64  `json:omitempty`  // 如果Price为空 就不输出
}

最后结果如下
在这里插入图片描述

通过map生产json
func main() {
	t1 := make(map[string]interface{})

	t1["k1"] = true
	t1["k2"] = 1234
	t1["k3"] = "hello world"

	b, err := json.MarshalIndent(t1, "", "  ")

	if err == nil {
		fmt.Println(string(b))
	}
}

生产结果如下

{                    
  "k1": true,        
  "k2": 1234,        
  "k3": "hello world"
}      

解码Json

可以使用json.Unmarshal()函数将JSON格式的文本解码为Go里面预期的数据结构

json.Unmarshal()函数的原型如下

func Unmarshal(data []byte, v interface{}) error

该函数的第一参数是json格式的文本( 字节序列 ) 第二个参数是目标输出容器 用于存放转化后的值

解析到结构体

代码演示如下 其实就是调用了下Unmarshal函数 此外并无其他难点

	t1 := IT{"itcast", []string{"Go", "C++"}, true, 666.66}
	b, err := json.MarshalIndent(t1, "", "  ")

	if err == nil {
		fmt.Println(string(b))
	}

	var t2 IT
	err = json.Unmarshal(b, &t2)

	if err == nil {
		fmt.Println(t2)
	}
解析到interface

演示代码如下

func main() {
	t1 := IT{"itcast", []string{"Go", "C++"}, true, 666.66}
	b, err := json.MarshalIndent(t1, "", "  ")

	if err == nil {
		fmt.Println(string(b))
	}

	var t interface{}
	err = json.Unmarshal(b, &t)

	m, ok := t.(map[string]interface{})

	if ok == true {
		for k, v := range m {
			fmt.Println(k, v)
		}
	}
}

上面代码的逻辑也很简单 我们使用了一个任意类型t来接受 json中的格式

最后我们使用一个类型断言来判断t的类型 如果断言成功 那么我们的m就会变成 map[string]interface{} 之后我们对于该类型进行遍历即可

文件操作

相关api介绍

建立和打开文件

建立文件

新建文件可以通过如下两个方法

func Create(name string) (file *File, err Error)

上面的函数会根据文件名创建一个新的文件 返回一个文件对象 创建文件的默认权限为0666 如果说对于权限不理解的同学可以参考我的这篇博客 Linux权限

返回的文件对象是可读写的

func NewFile(fd uintptr, name string) *File

根据文件描述符创建文件 返回一个文件对象

打开文件

我们可以通过下面两种方式打开一个文件

func Open(name string) (file *File, err Error)

我们可以通过Open函数+文件名的方式打开一个文件 但是此时的权限会变为只读 内部实现其实调用了Openfile

func OpenFile(name string, flag int, perm uint32) (file *File, err Error)

打开名称为name的文件 flag是打开方式 如只读 只写等 perm是权限

这里需要注意的是 如果文件已经创建 那么perm只能截断权限 而不能扩大权限

关闭文件
func (file *File) Close() 
写文件

写文件主要是通过下面几个函数实现

func (file *File) Write(b []byte) (n int, err Error)                   // 写入byte类型的数据到文件 
func (file *File) WriteAt(b []byte, off int64) (n int, err Error)      // 从 off位置开始写入byte类型的数据到文件
func (file *File) WriteString(s string) (ret int, err Error)           // 写入string类型的数据到文件 
读文件

读文件主要是通过下面几个函数实现

func (file *File) Read(b []byte) (n int, err Error)                   // 读取数据到b中
func (file *File) ReadAt(b []byte, off int64) (n int, err Error)      // 从off位置开始读取数据到b中 
删除文件
func Remove(name string) Error     // 调用函数就是删除名字为string的文件

示例代码

写文件
func main() {
	fout, err := os.Create("test.txt")

	if err != nil {
		fmt.Println(err)
	} // error

	defer fout.Close() // main函数结束前关闭文件

	for i := 0; i < 5; i++ {
		outstr := fmt.Sprintf("%s : %d\n", "hello go", i)
		fout.WriteString(outstr)
		fout.Write([]byte("abcd\n"))
	}
}

上面这段代码运行完毕之后我们就会在当前路径下创建一个 test.txt 文档 文档内容如下

在这里插入图片描述

读文件
	fin, err := os.Open("test.txt")

	if err != nil {
		fmt.Println(err)
	} // error

	defer fin.Close()

	b1 := make([]byte, 100, 200)

	fin.Read(b1)

	fmt.Println(string(b1))
拷贝文件

需求如下

  • 用户使用程序时输入两个命令行参数
  • 我们规定 第一个是源文件 第二个是拷贝文件
  • 我们要将源文件中的数据全部拷贝到拷贝文件中

代码表示如下

func main() {
	args := os.Args

	if args == nil || len(args) < 2 {
		fmt.Println("error ! need more para")
		return
	}

	src := args[1]
	desc := args[2]

	// fmt.Println(src, desc)
	fmt.Println(src, desc)
	fout, err1 := os.Open(src)

	// 下面的代码作用是打开两个文件
	if err1 != nil {
		fmt.Println(err1)
		return
	}

	defer fout.Close()

	// 这里无法写入是因为Open打开文件是只读
	// fin, err2 := os.Open(desc)
	fin, err2 := os.OpenFile(desc, os.O_WRONLY, 0666)

	if err2 != nil {
		fmt.Println(err2)
		return
	}

	defer fin.Close()

	b1 := make([]byte, 100, 200)
	n, _ := fout.Read(b1)
	fin.Write(b1[:n])

	fmt.Println("程序运行成功")
}

如何在IDE中设置命令行参数

我们可以右键文件 选择修改文件配置选项

在这里插入图片描述

之后在程序实参中选择即可 注意 不需要加 -

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.coloradmin.cn/o/1236562.html

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈,一经查实,立即删除!

相关文章

基于Apache部署虚拟主机网站

文章目录 Apache释义Apache配置关闭防火墙和selinux 更改默认页内容更改默认页存放位置个人用户主页功能基于口令登录网站虚拟主机功能基于ip地址相同ip不同域名相同ip不同端口 学习本章完成目标 1.httpd服务程序的基本部署。 2.个人用户主页功能和口令加密认证方式的实现。 3.…

Linux02 VIM编辑器

Linux02 VIM编辑器 基本上 vi/vim 共分为三种模式&#xff0c; 分别是命令模式&#xff08;Command mode&#xff09;&#xff0c;输入模式&#xff08;Insert mode&#xff09;和底线命令模式&#xff08;Last line mode&#xff09;。 三种状态进行切换 插入模式&#xff1a…

【机器学习】039_合理初始化

一、稳定训练 目标&#xff1a;使梯度值在更合理的范围内 常见方法如下&#xff1a; 将乘法变为加法 ResNet&#xff1a;当层数较多时&#xff0c;会加入一些加法进去 LSTM&#xff1a;如果时序序列较长时&#xff0c;把一些对时序的乘法做加法 归一化 梯度归一化&…

Java(五)(Object类,克隆,Objects类,包装类,StringBuilder,StringJoiner,BigDecimal)

目录 Object类 Object类的常见方法: 克隆 浅克隆 深克隆 Objects类 包装类 StringBuilder StringJoiner BigDecimal Object类 Object类是java中的祖宗类,因此,Java中所有的类的对象都可以直接使用object类提供的一些方法 Object类的常见方法: public String toStrin…

Redis-Redis持久化,主从哨兵架构详解

Redis持久化 RDB快照&#xff08;snapshot&#xff09; 在默认情况下&#xff0c; Redis 将内存数据库快照保存在名字为 dump.rdb 的二进制文件中。 你可以对 Redis 进行设置&#xff0c; 让它在“ N 秒内数据集至少有 M 个改动”这一条件被满足时&#xff0c; 自动保存一次数…

Mac- Iterm 2 (替换mac terminal 终端的下一代终端工具)

1.应用场景 主要用于macOS中作为终端工具使用, 执行终端命令, Iterm 2 (替换mac terminal 终端的下一代终端工具) 2.学习/操作 1.文档阅读 chatgpt & 其他资料 2.整理输出 2.1 是什么 Iterm 2 (替换mac terminal 终端的下一代终端工具) 2.2 为什么需要「应用场景」 macOS…

自定义类型之结构体

&#x1d649;&#x1d65e;&#x1d658;&#x1d65a;!!&#x1f44f;&#x1f3fb;‧✧̣̥̇‧✦&#x1f44f;&#x1f3fb;‧✧̣̥̇‧✦ &#x1f44f;&#x1f3fb;‧✧̣̥̇:Solitary-walk ⸝⋆ ━━━┓ - 个性标签 - &#xff1a;来于“云”的“羽球人”。…

操作系统 应用题 例题+参考答案(考研真题)

1.&#xff08;考研真题&#xff09;一个多道批处理系统中仅有P1和P2两个作业&#xff0c;P2比P1晚5ms到达&#xff0c;它们的计算和I/O操作顺序如下。 P1&#xff1a;计算60ms&#xff0c;I/O 80ms&#xff0c;计算20ms。 P2&#xff1a;计算120ms&#xff0c;I/O 40ms&…

会声会影2024出来了吗?会声会影2023怎么使用?

会声会影20247中文旗舰版 Corel VideoStudio 是一款功能强大的视频编辑软件&#xff0c;可以帮助用户创建高质量的视频作品。它提供了一系列完善的编辑功能&#xff0c;包括视频编辑、音频编辑、调色、特效、字幕、标题等。它还支持多种视频格式&#xff0c;可以将视频转换为多…

算法通关村第十二关-青铜挑战字符串

大家好我是苏麟 , 今天带来字符串专题 . 转换成小写字母 描述 : 给你一个字符串 s &#xff0c;将该字符串中的大写字母转换成相同的小写字母&#xff0c;返回新的字符串。 题目 : LeetCode 709.转换成小写字母 : 709. 转换成小写字母 分析 : 这个题可以先遍历整个字符串…

django+drf+vue 简单系统搭建 (4) 用户权限

权限控制是web中的重要组成部分。与以往的博客系统不同&#xff0c;本次工具页面仅支持注册用户。 每个注册用户都能访问到工具页面&#xff0c;并且提交自己的task来选择具体的工具来处理自己提交的文件。每个注册用户都只能访问到自己提交的task&#xff0c;而管理员则可以查…

uni-app:实现request请求的递归(设置request请求的访问次数),并且调用自定义方法给出返回值

一、效果展示 失败效果 成功效果 二、写入后端请求部分 分析 ①自定义一个模块common.js主要用于封装所有的请求函数 ②核心代码 function requestWithRetry(cmd, username, password, retryCount) {return new Promise((resolve, reject) > {uni.request({url: ip sys…

智能座舱架构与芯片- (13) 软件篇 下

四、面向服务的智能座舱软件架构 4.1 面向信号的软件架构 随着汽车电子电气架构向中央计算-域控制器的方向演进&#xff0c;甚至向车云一体化的方向迈进&#xff0c;适用于汽车的软件平台也需要进行相应的进化。 在传统的观念中&#xff0c;座舱域即娱乐域&#xff0c;座舱软…

【网络通信】浅析UDP与TCP协议的奥秘

在现代互联网中&#xff0c;UDP&#xff08;用户数据报协议&#xff09;和TCP&#xff08;传输控制协议&#xff09;是两种最常用的传输协议&#xff0c;它们被广泛应用于网络数据传输。尽管这两种协议都可以用来在网络上传输数据&#xff0c;但它们在设计目标、特点和适用场景…

Cesium 加载geojson数据类型点线面

1.获取geojson数据&#xff0c;本地新建一个.ts文件放置数据导出&#xff0c;并引入 获取geojson数据&#xff1a; DataV.GeoAtlas地理小工具系列 import { scGeojson } from ./geojson; 2.加载面 const addPolygonEvt () > {viewer.dataSources.add(Cesium.GeoJsonDataSo…

vue中data属性为什么是一个函数?

​&#x1f308;个人主页&#xff1a;前端青山 &#x1f525;系列专栏&#xff1a;Vue篇 &#x1f516;人终将被年少不可得之物困其一生 依旧青山,本期给大家带来vue篇专栏内容:vue-data属性 目录 为什么data属性是一个函数而不是一个对象&#xff1f; 一、实例和组件定义dat…

golang指针学习

package mainimport "fmt"func main() {name:"飞雪无情"nameP:&name//取地址fmt.Println("name变量的内存地址为:",&name)fmt.Println("name变量的值为:",name)fmt.Println("name变量的内存地址为:",nameP)fmt.Prin…

【CSH 入门基础 9 -- 输出 csh 脚本中每一句命令】

文章目录 输出csh脚本中每一句命令 输出csh脚本中每一句命令 在 csh 或 tcsh 脚本中&#xff0c;如果你想要输出脚本中的每一句执行&#xff0c;你可以在脚本的开头使用 -v&#xff08;verbose&#xff09;选项。这个选项会使得 shell 在执行命令前先打印出来。 要在脚本中使…

Macs Fan Control Pro:掌握您的Mac风扇,提升散热效率

在Mac的世界里&#xff0c;每一个细节都显得格外重要。而其中&#xff0c;风扇的控制与调节则显得尤为重要。然而&#xff0c;原生的Mac系统并不提供直观的风扇控制工具&#xff0c;这使得许多Mac用户在处理高负荷任务时&#xff0c;风扇无法有效地进行散热&#xff0c;导致机器…

HugeGraph安装与使用

1、HugeGraph-Server与HugeGraph-Hubble下载 HugeGraph官方地址&#xff1a;https://hugegraph.apache.org/ 环境为&#xff1a;linux 官网是有模块版本对应关系,尽量下载较新版本,hubble1.5.0之前是studio功能比较少。官网已经下架server,其他模块下载也比较慢。可以在网上找…