首页 > 系统相关 >正则表达式(C、C++、Python、Shell)

正则表达式(C、C++、Python、Shell)

时间:2022-10-21 18:26:40浏览次数:79  
标签:regex Shell 匹配 Python C++ 正则表达式 str 字符串 reg

撰写本文档的初衷本来是想介绍正则表达式怎么写,但是百度一搜,正则表达式的教程的质量已经相当高,我便不在班门弄斧了。正则表达式是一种方法,在不同的语言中,它的应用样式可能会不同,但是方法是一样的,只要了解好标准的正则表达式如何写,就能应付其他语言下的正则表达式样式。

那本文主要收集了常用编程语言下的应用样式 ,让大伙认识正则表达式在不同语言下的应用,至于基础,请大伙移步专业的教程。https://www.runoob.com/regexp/regexp-tutorial.html

 

一、正则表达式类型

正则表达式分为:①基础正则表达式 ②扩展正则表达式

基础正则表达式是最先提出和应用的,后来发现有些情况匹配能力有限,所以加入了扩展正则表达式;

比如说有这么一段字符串:“A=1,B=2,C=3,D=4“

我们计划把B的值提取出来,用基础正则匹配“B=”和","中间的,但是却提取出“2,C=3“

这时候需要拓展正则表达式中的贪婪模式(尽可能多)和非贪婪模式(尽可能少)来解决

加入扩展正则表达式,在基础正则表达式的匹配结果上进一步进行过滤。

 

在线验证正则表达式的工具:

https://tool.oschina.net/regex/

https://regex101.com/

 

二、不同编程语言下的应用

1、C语言

在c语言中,用regcomp、regexec、regfree 和regerror处理正则表达式。处理正则表达式分三步:

①编译正则表达式,regcomp

②匹配正则表达式,regexec

③释放正则表达式,regfree

/*
函数说明:Regcomp将正则表达式字符串regex编译成regex_t的形式,后续regexec以此进行搜索。
参数说明:
    Preg:一个regex_t结构体指针。
    Regex:正则表达式字符串。
    Cflags:是下边四个值或者是他们的或(|)运算。
        REG_EXTENDED:使用POSIX扩展正则表达式语法解释的正则表达式。如果没有设置,基本POSIX正则表达式语法。
        REG_ICASE:忽略字母的大小写。
        REG_NOSUB:不存储匹配的结果。
        REG_NEWLINE:对换行符进行“特殊照顾”,后边详细说明。
返回值:
    0:表示成功编译;
    非0:表示编译失败,用regerror查看失败信息
*/
int regcomp(regex_t *preg, const char *regex, int cflags);


/*
函数说明: Regexec用来匹配正则文本。
参数说明:
    Preg:由regcomp编译好的regex_t结构体指针,
    String:要进行正则匹配的字符串。
    Nmatch:regmatch_t结构体数组的大小
    Pmatch:regmatch_t结构体数组。用来保存匹配结果的子串位置。
    regmatch_t结构体定义如下
        typedef struct {
            regoff_t rm_so;
            regoff_t rm_eo;
        } regmatch_t;
        rm_so,它的值如果不为-1,表示匹配的最大子串在字符串中的起始偏移量,rm_eo,表示匹配的最大字串在字符串的结束偏移量。
    Eflags: REG_NOTBOL和REG_NOTEOL为两个值之一或二者的或(|)运算,稍后会介绍。
返回值:
    0:表示成功编译;
    非0:表示编译失败,用regerror查看失败信息
*/
int regexec(const regex_t *preg, const char *string, size_t nmatch, regmatch_t pmatch[], int eflags);


/*
函数说明:用来释放regcomp编译好的内置变量。
参数说明:
    Preg:由regcomp编译好的regex_t结构体指针。
*/
void regfree(regex_t *preg);


/*
函数说明:Regcomp,regexec出错时,会返回error code并且为非0,此时就可以用regerror得到错误信息。
参数说明:
    Errcode:Regcomp,regexec出错时的返回值
    Preg:经过Regcomp编译的regex_t结构体指针。
    Errbuf:错误信息放置的位置。
    errbuf_size:错误信息buff的大小。
*/
size_t regerror(int errcode, const regex_t *preg, char *errbuf, size_t errbuf_size);
//比如字符串:<html>value</html>,想要匹配固定字符之间的内容:

#include <stdio.h>
#include <stdlib.h>
#include <sys/types.h>
#include <regex.h>
 
int main (void)
{
    char ebuff[256];	//装载错误信息
    int ret;			
    int cflags;
    regex_t reg;
 
    cflags = REG_EXTENDED | REG_ICASE | REG_NOSUB;
 
    char *test_str = "Hello World";
    char *reg_str = "H.*";
 
    ret = regcomp(&reg, reg_str, cflags);	//编译
    if (ret) {   //编译失败
        regerror(ret, &reg, ebuff, 256);
        fprintf(stderr, "%s\n", ebuff);
        regfree(&reg);
        return -1;
    }   
 
    ret = regexec(&reg, test_str, 0, NULL, 0);	//匹配
    if (ret) {	//匹配失败
        regerror(ret, &reg, ebuff, 256);
        fprintf(stderr, "%s\n", ebuff);
        regfree(&reg);
        return -1;
    }   
 
    regerror(ret, &reg, ebuff, 256);	//装载匹配成功结果
    fprintf(stderr, "result is:\n%s\n", ebuff);
 
    regfree(&reg);	//释放
    return 0;
}

2、C++

在C++中利用正则表达式需要regex库,在头文件<regex>中包含了多个我们使用正则表达式时需要用到的组件,大致有:

  

regex

表示有一个正则表达式类,比如:regex pattern("(.{3})(.{2})_(\d{4})!")

regex_match

全文匹配,要求整个字符串符合正则表达式的匹配规则。用来判断一个字符串和一个正则表达式是否模式匹配,返回一个 bool 值,true 为匹配,false 为不匹配。匹配的含义是目标字符串必须完全和正则表达式相匹配,不能有多余的字符,如果需要部分匹配则应使用regex_search

regex_search

搜索匹配,根据正则表达式来搜索字符串中是否存在符合规则的子字符串。 能和正则表达式相匹配就返回true

regex_replace

替换匹配,即可以将符合匹配规则的子字符串替换为其他字符串。要求输入一个正则表达式,以及一个用于替换匹配子字符串的格式化字符串。这个格式化字符串可以通过转义序列引用匹配子字符串中的部分内容

sregex_iterator

迭代器适配器,调用regex_search来遍历一个string中所有匹配的子串

smatch/match_results

容器类,保存在string中搜索的结果。如果匹配成功,这些函数将成功匹配的相关信息保存在给定的smatch对象中

//比如字符串:Hello_2018

#include <iostream>
#include <string>
#include <regex>
using namespace std;
 
int main()
{
    string str = "Hello_2018";
    smatch result;
    regex pattern("(.{5})_(\\d{4})");	//匹配5个任意单字符 + 下划线 + 4个数字

    if (regex_match(str, result, pattern))
    {
        cout << result[0] << endl;		//完整匹配结果,Hello_2018
        cout << result[1] << endl;		//第一组匹配(括号)的数据,Hello
        cout << result[2] << endl;		//第二组匹配(括号)的数据,2018
      
      	//result[]与result.str()这两种方式能够获得相同的值
      
        cout<< result.str() << endl;	//完整结果,Hello_2018
        cout<< result.str(1) << endl;	//第一组匹配(括号)的数据,Hello
        cout << result.str(2) << endl;	//第二组匹配(括号)的数据,2018
    }
}

3、Python

实现网络爬虫必然离不开正则表达式,Python的正则表达式主要用re库实现。

移步专业教程:https://www.runoob.com/python/python-reg-expressions.html

//比如字符串:<html>value</html>,想要匹配固定字符之间的内容:

import re
str='<html>value</html>'
pattern=re.compile('<html>(.*)</html>')   #匹配<html>与</html>之间的内容
result=pattern.findall(str)
print(result)


//贪婪和非贪婪匹配
str = "a123b456b"

print re.findall(r"a(.+?)b", str)
#输出['123']#?控制只匹配0或1个,所以只会输出和最近的b之间的匹配情况

print re.findall(r"a(.+)b", str)
#输出['123b456']

print re.findall(r"a(.*)b", str)
#输出['123b456']


//多行匹配
str = "a23b\na34b"

re.findall(r"a(\d+)b.+a(\d+)b", str)
#输出[]
#因为不能处理str中间有\n换行的情况

re.findall(r"a(\d+)b.+a(\d+)b", str, re.S)
#s输出[('23', '34')]

4、Shell

表达式在Linux编程中很常用,Shell脚本编程,文本处理的3把瑞士军刀sed,awk和grep都离不开正则表达式。Shell脚本中正则表达式的应用,可以参考我写的关于sed命令的文章。

 

标签:regex,Shell,匹配,Python,C++,正则表达式,str,字符串,reg
From: https://www.cnblogs.com/darren-channel/p/16814415.html

相关文章

  • python基础-数据类型间的转换
    数据类型转换:将自身数据类型转化成新的数据类型,并拥有新数据类型相关操作的过程;为方便更好的帮助处理业务,将数据变更为更适合业务场景的类型;a='1', 此时想使用数字的......
  • python
    基础赋值打印word="""12345段落"""print(word[0:6])输出结果12345换行的话是空格字符不换行输出print('xyz',end="")print('dnf')......
  • Python 发送邮件的几种情况
    本次记录一下Python发送邮件的几种情况:1、正常发送2、正文带图片3、正文带表格4、正文带附件 首先来看一下Python发送邮件使用到的模块##导入模块fromemail.mi......
  • Visual Code配置C/C++
    1.前言VSCode和以前的Visualstudio开发环境不一样,只是代码编辑器,如果需要运行代码C/C++,需要额外安装编译器。在Linux环境下,一般系统自带了gcc编译器,但是windows环境没......
  • python的高级特性-迭代概念
    迭代Python内置的enumerate函数可以把一个list变成索引-元素对,这样就可以在for循环中同时迭代索引和元素本身>>>fori,valueinenumerate(['A','B','C']):...prin......
  • C/C++停车场模拟(栈和队列)
    C/C++停车场模拟(栈和队列)【讨论问题2】栈和队列的应用[问题描述]设停车场是一个可停放n辆汽车的狭长通道,且只有一个大门可供汽车进出。汽车在停车场内按车辆到达时间的......
  • C/C++single
    #include<iostream>#include<unistd.h>#include<csignal>#include<string.h>usingnamespacestd;voidsignal_handler(intsignal){ cout<<"Caughtsignalnum......
  • Python pygame新手入门基础教程
    pygame简介 pygame可以实现python游戏的一个基础包。  pygame实现窗口 初始化pygame,init()类似于java类的初始化方法,用于pygame初始化。pygame.init()......
  • shell命令操作(jenkins执行后判断shell执行的对与错)
    字符截取https://blog.csdn.net/JineD/article/details/124196546 条件判断http://www.caotama.com/1903002.htmlstrA=$(curl--location--requestPOST'https://b......
  • python中numpy切片问题
    方式1:逗号前表示行,冒号表示从该行的第几个到第几个(包含头不包含尾)方式2:逗号在后,表示列,冒号表示从该列的第几个到第几个(包含头不包含尾)......