Golang每日一库之regex
本文地址: https://www.cnblogs.com/zichliang/p/17387436.html
Golang日库合集:https://www.cnblogs.com/zichliang/category/2297320.html
简介
正则表达式是一种用来查询、匹配或替换字符串的技术。你可以使用它来找到符合特定模式的文本、删除或替换匹配的字符串。它可以用于各种编程语言和工具中,如Perl、Python、JavaScript、Java等等。
一句话概括就是,“正则表达式可以帮你快速、简便地处理需要查找、匹配或替换的文本内容,它可以大大提高程序的效率。”
正则介绍
正则表达式通常可以分为以下几个步骤:
- 定义正则表达式模式:即给出需要匹配或查找的文本规则,如匹配所有以"A"开头的单词,模式可以是 "^A\w+"。
- 编译正则表达式:将正则表达式模式编译成程序可识别的格式。
- 指定匹配文本:输入需要进行匹配操作的文本,如一段英语文章。
- 进行匹配操作:程序会根据输入的正则表达式和匹配文本进行匹配操作,搜索所有与正则表达式模式匹配的子串。
- 获取匹配结果:输出匹配到的所有子串,包括位置、长度,或将它们替换成所需要的格式。
元字符
上文说的第一步与第二步匹配特定字符或字符类型的字符在正则表达式中具有特殊含义。一般来说,它们都是特殊符号或字母,用于匹配某个字符类或执行某种操作。
这里就不列举了
推荐个网站: 里面包含了基本上所有的元字符: https://www.runoob.com/regexp/regexp-metachar.html
Golang中的正则
其实非常简单主要分为三步
- 正则( 针对字符串匹配规则)
- 元字符(基本上大同小异)
- 方法(特定语言有特定方法)
Golang 中常用的元字符:
- .:匹配任意单个字符,除了换行符和回车符。
- ^:匹配输入字符串的开始位置。
- $:匹配输入字符串的结束位置。
- *:匹配前面的字符(包括字符类)零次或多次。
- +:匹配前面的字符(包括字符类)一次或多次。
- ?:匹配前面的字符(包括字符类)零次或一次。
- |:分隔两个可选模式,匹配任意一个模式。
- []:匹配其中的任意一个字符。可以使用短横线表示范围,如 [a-z] 表示匹配任意小写字母。
- \d:匹配任意一个数字字符,相当于 [0-9]。
- \w:匹配任意一个字母、数字或下划线,相当于 [a-zA-Z0-9_]。
- \s:匹配任意一个空白字符,包括空格、制表符、换行符等。
Golang中的函数和方法介绍
在 Golang 中,标准库 regexp 提供了一系列正则操作函数,下面是这些函数的简要介绍:
Compile(expr string) (*Regexp, error):将一个字符串编译成一个正则表达式对象Regexp。如果编译失败,会返回一个非nil的错误对象。CompilePOSIX(expr string) (*Regexp, error):类似于Compile函数,但是将正则表达式解释为 POSIX 语法。MustCompile(expr string) *Regexp:类似于Compile函数,但是在编译失败时会直接抛出一个 panic。MustCompilePOSIX(expr string) *Regexp:类似于MustCompile函数,但是将正则表达式解释为 POSIX 语法。Match(pattern string, b []byte) (bool, error):判断一个字节数组中是否包含指定的正则表达式。MatchString(pattern string, s string) (bool, error):判断一个字符串中是否包含指定的正则表达式。MatchReader(pattern string, r io.RuneReader) (bool, error):类似于Match函数,但是适用于io.RuneReader类型。MatchRegexp(r *Regexp, s string) bool:对一个字符串执行已编译的正则表达式对象Regexp进行匹配。MatchReaderRegexp(r *Regexp, r io.RuneReader) bool:类似于MatchRegexp函数,但是适用于io.RuneReader类型。QuoteMeta(s string) string:将一个字符串中的元字符以外的所有字符都转义,使它们成为字面量。
除此之外,Regexp 对象还提供了一系列操作方法,例如:
Find(b []byte) []byte:返回第一个匹配的子字符串。FindAll(b []byte, n int) [][]byte:返回所有匹配的子字符串,n 表示最大匹配次数。FindAllIndex(b []byte, n int) [][]int:返回所有匹配的子字符串的起止索引,n 表示最大匹配次数。FindIndex(b []byte) (loc []int):返回第一个匹配的子字符串的起止索引。FindString(s string) string:返回第一个匹配的子字符串。FindAllString(s string, n int) []string:返回所有匹配的子字符串,n 表示最大匹配次数。FindAllStringIndex(s string, n int) [][]int:返回所有匹配的子字符串的起止索引,n 表示最大匹配次数。FindStringIndex(s string) (loc []int):返回第一个匹配的子字符串的起止索引。FindAllSubmatch(b []byte, n int) [][][]byte返回的是字节切片的切片的切片FindAllSubmatchIndex(b []byte, n int) [][]int返回所有匹配子串的开始和结束的字符索引位置。FindAllStringSubmatch(s string, n int) [][]string返回的是字符串切片的切片的切片。FindAllStringSubmatchIndex(s string, n int) [][]int返回各个子串的开始和结束的索引值,ReplaceAll(src []byte, repl []byte) []byte:将 src 中的所有匹配项替换为 repl,返回替换后的结果。ReplaceAllString(src, repl string) string:类似于ReplaceAll函数,但是输入输出都是字符串类型。Split(s string, n int) []string:将 s 按照正则表达式分割,n 表示最大分割次数。SplitN(s string, n int) []string:类似于Split函数,但是只分割前 n 个子字符串。
这些函数和方法可以满足我们对正则表达式进行各种查询、替换、分割等常见操作的需求。
示例
Compile 和 MustCompile
在 Golang 中,我们可以使用 Compile 函数和 MustCompile 函数来将正则表达式字符串编译为一个 Regexp 对象。
这两个函数的作用是相同的,都是将正则表达式字符串编译成一个正则表达式对象,只不过 MustCompile 函数在编译失败时会直接抛出一个 panic。
Compile
// Compile 函数的使用方式
re, err := regexp.Compile(`\d+`)
if err != nil {
// 正则表达式编译失败
return
}
// 使用编译后的正则表达式对象
fmt.Println(re.MatchString("123"))
结果
true
MustCompile
// MustCompile 函数的使用方式
re = regexp.MustCompile(`\d+`)
fmt.Println(re.MatchString("456"))
结果
true
FindAllSubmatch和FindAllStringSubmatch
FindAllSubmatch 方法是 Golang 中 Regexp 对象提供的一个方法。
用于在指定字符串中查找所有符合正则表达式规则的子字符串,并返回子字符串所对应的分组信息及匹配位置。
其函数签名如下:
func (re *Regexp) FindAllSubmatch(b []byte, n int) [][][]byte
func (re *Regexp) FindAllSubmatchIndex(b []byte, n int) [][]int
func (re *Regexp) FindAllStringSubmatch(s string, n int) [][]string
func (re *Regexp) FindAllStringSubmatchIndex(s string, n int) [][]int
FindAllSubmatch 和 FindAllStringSubmatch 方法都用于在字符串中查找所有匹配正则表达式的子字符串,它们返回的是一个包含所有匹配子串和索引位置的二维切片。
FindAllStringSubmatchIndex 方法返回一个二维的整数切片,每个子切片表示一次匹配,每个子切片中的两个整数分别表示匹配子串在源字符串中的开始和结束位置的索引。
FindAllSubmatchIndex 方法也返回一个二维的整数切片,不同的是,每个子切片中都包含一系列整数,每两个整数表示匹配的一组子表达式在源字符串中的开始和结束位置的索引。
其实说的还是有些笼统 直接看例子
package main
import (
"fmt"
"regexp"
"strings"
)
func main() {
content := `111 aba 1024 bbb 2048 ccc aba aba`
pattern := `aba`
compile, _ := regexp.Compile(pattern)
results := compile.FindAllSubmatch([]byte(content), -1)
fmt.Println(compile.FindAllSubmatchIndex([]byte(content), -1))
for _, result := range results {
fmt.Println("FindAllSubmatch>>>>>", result)
fmt.Println("FindAllSubmatch>>>>>", result[0])
fmt.Println("FindAllSubmatch>>>>>", string(result[0]))
}
fmt.Println(strings.Repeat("*", 100))
results1 := compile.FindAllStringSubmatch(content, -1)
fmt.Println(compile.FindAllStringSubmatchIndex(content, -1))
for _, result := range results1 {
fmt.Println("FindAllStringSubmatch>>>>>", result)
fmt.Println("FindAllStringSubmatch>>>>>", result[0])
}
}
结果如下:

例子2:
如果我们需要正则提取网站该如何实现呢?
package main
import (
"fmt"
"regexp"
"strings"
)
func main() {
content := `<a href="https://www.jd.com" target="_blank">京东</a> <a href="https://www.taobao.com" target="_blank">淘宝</a>`
pattern := `<a href="(.*?)" target="_blank">(.*?)</a>`
compile, _ := regexp.Compile(pattern)
results := compile.FindAllSubmatch([]byte(content), -1)
/*
[][][]byte
[]byte=""
// 一旦加了括号等于分了组 后面会向这个切片追加值,所以下文只要切片取第二个值就行了 多分组就以此类推
[
[<a href="https://www.jd.com" target="_blank">京东</a>,https://www.jd.com,京东]
[<a href="https://www.taobao.com" target="_blank">淘宝</a>,https://www.taobao.com,淘宝]
]
*/
for _, result := range results {
fmt.Println(strings.Repeat("*", 100))
fmt.Println(string(result[0]), string(result[1]), string(result[2]))
}
}
结果

本文地址: https://www.cnblogs.com/zichliang/p/17387436.html
Golang日库合集:https://www.cnblogs.com/zichliang/category/2297320.html
Golang每日一库之regex的更多相关文章
- Golang每日一库之bcrypt
本文 官方文档: https://pkg.go.dev/golang.org/x/crypto/bcrypt 前言 之前讲过JWT Token https://www.cnblogs.com/zich ...
- Go 每日一库之 go-carbon,优雅的golang日期时间处理库
Carbon 是一个轻量级.语义化.对开发者友好的 golang 时间处理库,支持链式调用. Carbon 已被 awesome-go 收录, 如果您觉得不错,请给个 star 吧. github.c ...
- Go 每日一库之 flag
缘起 我一直在想,有什么方式可以让人比较轻易地保持每日学习,持续输出的状态.写博客是一种方式,但不是每天都有想写的,值得写的东西. 有时候一个技术比较复杂,写博客的时候经常会写着写着发现自己的理解有偏 ...
- Golang实现requests库
Golang实现requests库 简单的封装下,方便使用,像python的requests库一样. Github地址 Github 支持 GET.POST.PUT.DELETE applicatio ...
- Golang 的 TOML库
TOML 的全称是 Tom's Obvious, Minimal Language,因为它的作者是 GitHub 联合创始人 Tom Preston-Werner. TOML 的目标是成为一个极简的配 ...
- 『Golang』—— 标准库之 os
Golang 的 os 库基本承袭 Unix 下 C 语言的用法 path 库: func Base(path string) string //取文件名,不含目录部分 func Dir(path s ...
- Go 每日一库之 viper
简介 上一篇文章介绍 cobra 的时候提到了 viper,今天我们就来介绍一下这个库. viper 是一个配置解决方案,拥有丰富的特性: 支持 JSON/TOML/YAML/HCL/envfile/ ...
- Go 每日一库之 fsnotify
简介 上一篇文章Go 每日一库之 viper中,我们介绍了 viper 可以监听文件修改进而自动重新加载. 其内部使用的就是fsnotify这个库,它是跨平台的.今天我们就来介绍一下它. 快速使用 先 ...
- Golang编写动态库实现回调函数
Golang编写动态库实现回调函数 我们现在要做一个动态库,但是C++实在是比较难,于是就想能不能用更简单的golang来实现,golang也就是最近的版本才支持编译成动态库,在网上也没找到可用的案例 ...
- golang命令行库cobra的使用
简介 Cobra既是一个用来创建强大的现代CLI命令行的golang库,也是一个生成程序应用和命令行文件的程序.下面是Cobra使用的一个演示: Cobra提供的功能 简易的子命令行模式,如 app ...
随机推荐
- win10 python + selenium 环境搭建
一.安装python3 1.下载地址: https://www.python.org/downloads/windows/ 直接选择最新版,下拉 file列表中,选择win10版 64位 Windo ...
- 了解RTT 和RTO 对于TCP 重传的影响
前言 我们已经在很多地方了解TCP 的功能和常用字段.但是TCP 传输发生的异常情况总是让我们很棘手,不知改如何处理.陷入迷茫之中.本文章只针对RTT 和RTO 做了解. 描述 RTT (Round ...
- nios verify failed 问题解决。
nios 调试时碰到上图所示问题.根据下载地址可以判断下载flash.sdram都成功,这里说明电路设计和焊接都没有问题. 但是在flash地址verify failed between adress ...
- VSCode 快捷键,简化操作
一. 区域代码快捷键 1. 折叠所有 折叠所有区域代码的快捷: ctrl + k ctrl + 0 ; 展开所有折叠区域代码的快捷:ctrl +k ctrl + J ; 2. 按层 ...
- java生态下的后端开发都有哪些技术栈?
前言 我08年毕业,那时(2003-2010)C#还比较时髦的,大学跟着老师进修的,毕业后就从事winform窗体应用程序开发.慢慢的web网站兴起,就转到aps.net开发,再到后来就上了另一艘船( ...
- 为什么 C# 可能是最好的第一编程语言
纵观神州大地,漫游中华互联网,我看到很多人关注为什么你应该开始学习JavaScript做前端,而对blazor这样的面向未来的框架有种莫名的瞧不起,或者为什么你应该学习Python作为你的第一门编程语 ...
- # 1. C++概述
1. C++概述 1.1 c++简介 "c++"中的++来自于c语言中的递增运算符++,该运算符将变量加1.c++起初也叫"c with clsss".通过名称 ...
- KCP协议浅析
概述 KCP协议结合了TCP和UDP协议的特点,是一个快速可靠的协议. 引述官方介绍: KCP是一个快速可靠协议,能以比 TCP浪费10%-20%的带宽的代价,换取平均延迟降低 30%-40%,且最大 ...
- maui BlazorWebView+本地html (vue、uniapp等都可以) 接入支付宝sdk 进行支付宝支付 开发 Android app
首先添加支付宝sdk的绑定库 nuget 包:Chi.MauiBinding.Android.AliPay 项目地址:https://github.com/realZhangChi/MauiBindi ...
- 《3D编程模式》写书-第1天记录
大家好,我现在开始写书了,书名为:<3D编程模式> 我会在本系列博文中记录写书的整个过程,感谢大家支持! 这里是所有的的写书记录: <3D编程模式>写书记录 为什么写书 去年我 ...