程序员必备技能——正则表达式
Posted 攻城狮白玉
tags:
篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了程序员必备技能——正则表达式相关的知识,希望对你有一定的参考价值。
目录
前言
当我们在通过爬虫抓取网页数据的时候,请求回来的网页数据其实是一个很长很长的字符串。
而整个网页里面的内容并不全都是我们想要的,我们可能要的只是其中的一些字段。这个时候我们在字符匹配的时候就会用到正则表达式。
或者当我们前端页面要对一些输入框输入的内容进行校验时(比如手机号码,身份证号),我们也会用到正则表达式。
当我们想要对于特定的一类字符串进行替换的时候,我们也会用到正则表达式
一、什么是正则表达式
前面说了那么多,那什么是正则表达式呢?正则表达式,又叫做规则表达式(Regular Expression,在代码中常简写为regex、regexp或RE)
正则表达式的作用,说通俗一点就是可以在已有的字符串上面检查看看有没有符合要求的子字符串
正则优点:速度快、效率高、准确性高
正则缺点:新手上手难度有点高
正则表达式并不是属于某种特定的计算机语言,它应该算作是一种字符串框架,在很多中语言都有其对应的实现方法。
接下来咱们介绍一下关于正则表达式的几个概念
二、元字符
觉有固定含义的字符,每个元字符就只能匹配一个字符
常用的元字符
字符 | 描述 |
. | 匹配除了换行符以外的任意字符 |
\\w | 匹配字符或者数字或者下划线。(等价于'[A-Za-z0-9_]') |
\\s | 匹配任意的空白符。(等价于 [ \\f\\n\\r\\t\\v]) |
\\d | 匹配数字。(等价于 [0-9]) |
\\n | 匹配一个换行符 |
\\t | 匹配一个制表符 |
^ | 匹配字符串的开始 |
$ | 匹配字符串的结尾 |
\\W | 匹配非字符或数字或下划线。(跟\\w的作用相反,等价于 '[^A-Za-z0-9_]') |
\\D | 匹配非数字。(跟\\d的作用相反,等价于 [^0-9]) |
\\S | 匹配非空白符。(跟\\s的作用相反,等价于 [^ \\f\\n\\r\\t\\v]) |
a|b | 匹配字符a或字符b |
[...] | 匹配字符组中的字符 |
[^...] | 匹配除了字符组中字符的所有字符 |
三、数量限定符
量词,这个是用于控制元字符出现的次数
字符 | 描述 |
* | 重复零次或更多次 |
+ | 重复一次或更多次 |
? | 重复零次或一次 |
{n} | 重复n次 |
{n,} | 重复n次或更多次 |
{n,m} | 重复n到m次 |
四、正则匹配实战
讲了那么多,我们进行实战,我们可以通过一些在线的表达式工具进行测试
接下来,我们对于下面这段话进行一个正则筛选,
攻城狮白玉的手机号是:12110120119,攻城狮白玉的电话是:020-00000000
攻城狮白玉的博客是https://blog.csdn.net/zhh763984017
攻城狮白玉的公众号是Baiyu96
首先我们要找到我的电话号码,我们都知道,手机号码是11位的,所以我们可以用\\d{11}来进行匹配
如果我要找到我的博客地址https://blog.csdn.net/zhh763984017
我们可以用[a-zA-z]+://[^\\s]*来进行匹配。这串正则的解析如下:
- [a-zA-Z]+:表示在冒号:前有一个或多个字母无论大小写
- //[^\\s]*表示在双斜杠后面的所有非空格的字符都是
这样子看似能够把网址都匹配出来,但是其实也是有bug的,就是上面这个链接匹配必须保证你的url网址后面没有跟着其他的字符。否则用上面的匹配规则还是有问题的
如下图,我在链接后面加了东西
五、贪婪匹配和惰性匹配
5.1 惰性匹配 .*?
.*?是尽可能少的匹配,当出现多个结果的时候时【?】是让【*】尽可能少的出现的长度。
例如:我要找到我的名字【攻城狮白玉】,就得使用惰性匹配。惰性匹配在我们使用爬虫的时候也会经常用到,其实也不仅仅是爬虫,其他的数据定位也会用的比较多。
5.2 贪婪匹配 .*
如果使用贪婪匹配的话,会怎么样呢?它会贪婪的找到长度最长的,符合开头字符是【攻】结尾是【玉】的字符串,也就出现了下面的“攻城狮白玉的手机号是:12110120119,攻城狮白玉”。这么长的字符串
六、不同语言的正则表达式
前面我说过,正则表达式其实是一种与语言无关的文本处理工具。在不同语言下面对于正则的实现方式也是不一样的。这里我列举的python、C#、golang对于筛选手机号码的正则匹配。
6.1 Python示例
python内置的re库可以实现正则表达式
import re
ex_str="""
攻城狮白玉的手机号是:12110120119,攻城狮白玉的电话是:020-00000000
攻城狮白玉的博客是https://blog.csdn.net/zhh763984017
攻城狮白玉的公众号是Baiyu96
"""
obj = re.compile(r"\\d{11}")
ret = obj.finditer(ex_str)
for it in ret:
print(it.group())
6.2 C#示例
C#可以使用.net内置的Regex 类。使用前要引用System.Text.RegularExpressions;
using System;
using System.Text.RegularExpressions;
public class TestRe
{
private static void showMatch(string text, string expr)
{
Console.WriteLine("正则表达式是: " + expr);
MatchCollection mc = Regex.Matches(text, expr);
foreach (Match m in mc)
{
Console.WriteLine(m);
}
}
public static void Main()
{
string str=@"攻城狮白玉的手机号是:12110120119,攻城狮白玉的电话是:020-00000000
攻城狮白玉的博客是https://blog.csdn.net/zhh763984017
攻城狮白玉的公众号是Baiyu96";
string expr = @"\\d{11}";
showMatch(str,expr);
}
}
6.3 Golang示例
通过go语言内置的regexp库,我们也可以实现正则表达式
package main
import (
"fmt"
"regexp"
)
func main() {
ex_str :=`攻城狮白玉的手机号是:12110120119,攻城狮白玉的电话是:020-00000000
攻城狮白玉的博客是https://blog.csdn.net/zhh763984017
攻城狮白玉的公众号是Baiyu96`
re, _ := regexp.Compile(`\\d{11}`)
c := re.FindAllString(ex_str,-1)
fmt.Println(c)
}
这里只是举例了三种编程语言的正则表达式的实现,在其他编程语言,如C++、js、java等语言都有其对应的实现方式。包括在咱们的linux命令行,通过grep也可以实现对于命令行输出结果进行正则匹配。
总结
从本文的介绍可知,正则表达式的应用场景大致可以分为查找、校验、替换三个。不过文中我们只是演示了如何寻找,但是其实寻找到了之后就可以进行替换。校验的话,则是说输入的内容要满足正则表达式的匹配规则,否则就校验不通过。正则表达式与某种特定的计算机编程语言无关。不同的计算机编程语言都有相应的实现方法。
写在后面
如果觉得有用的话,麻烦动动各位发财的小手指,给个一键三连支持一下攻城狮白玉,并把本文分享给更多的小伙伴。你的简单支持,我的无限创作动力
如果有想看的内容,也可以在博文底部评论,我会整理出来给到大家~
以上是关于程序员必备技能——正则表达式的主要内容,如果未能解决你的问题,请参考以下文章