c++11 regex 与 PCRE库使用
简介
PCRE
PCRE(Perl Compatible Regular Expressions)是一个Perl库,包括 perl 兼容的正则表达式库。这些在执行正规表达式模式匹配时用与Perl 5同样的语法和语义是很有用的。Boost太庞大了,使用boost regex后,程序的编译速度明显变慢。测试了一下,同样一个程序,使用boost::regex
编译时需要3秒,而使用pcre不到1秒。因此改用pcre来解决C语言中使用正则表达式的问题
C++11 regex
c++ regex 库,是c++11标准引入的功能,通过 #include <regex>
来使用。其中主要的算法为regex_search, regex_match, regex_replace
示例
假如我们需要处理一段特殊字符串,分析其特征发现使用正则可以很好的捕获想要获取的数据,假设这段字符串为"Makefile auth auth.c gen_sig.c gensig license.lic"
,我们需要字符串里面的文件名,下面使用c pcre库和c++11 regex简单实现捕获特殊字符串数据(不使用boost regex原因是Boost太庞大了,使用boost regex后,程序的编译速度明显变慢)。
pcre库捕获特殊字符串示例
首先对pcre库函数进行简单的封装(需要引入头文件#include <pcre.h>
需要链接 -lpcre
),这样会更方便使用,函数如下:
///
//函数说明 : pcre正则解析字符串
//参数说明 : [pSubject] 规则字符串
// [nSubjectLen] 字符串长度
// [pPattern] 正则规则
// [pMatchVec] 捕获字符串偏移量
// [nMatchVec] 捕获字符串偏移量的最大长度
// [nMatchGroup] 捕获组数
//返回值 : true代表命中规则,false代表未命中
//作者 : buding
//修改日期 : 2021-09-22
bool PcreMatchCapture(char* pSubject, size_t nSubjectLen, const char* pPattern, int* pMatchVec, size_t nMatchVec, int& nMatchGroup)
{
pcre* pPcre = NULL;
const char* pError = NULL;
int nErrorOffset = 0;
pPcre = pcre_compile(pPattern, 0, &pError, &nErrorOffset, NULL);
if (!pPcre)
{
printf("[pcre] compile failed at offset %d: %s\n", nErrorOffset, pError);
return false;
}
nMatchGroup = pcre_exec(pPcre, NULL, pSubject, nSubjectLen, 0, 0, pMatchVec, nMatchVec);
if (nMatchGroup < 0)
{
pcre_free(pPcre);
return false;
}
pcre_free(pPcre);
return true;
}
分析字符串"Makefile auth auth.c gen_sig.c gensig license.lic"
不难发现字符串特征都是以空白隔开的,其正则表达式也很容易写出(\S+)\s+(\S+)\s+(\S+)\s+(\S+)\s+(\S+)\s(\S+)
(\S: 匹配任何可见字符。等价于[^ \f\n\r\t\v] ; \s: 匹配任何不可见字符,包括空格、制表符、换页符等等,等价于[ \f\n\r\t\v])。
正则表达式语法网上资料很多,这里就不做过多解释了。
接下来就要解析字符串中的特定内容:代码如下:
///
//函数说明 : pcre正则解析字符串
//参数说明 : [linedata] 规则字符串
// [cb_arg] 回调参数,返回捕获特定内容
//返回值 : 无
//作者 : buding
//修改日期 : 2021-09-22
void * MatchStrFileName(std::string linedata, void *cb_arg)
{
int nMatchGroup = 0;
int MatchVec[30] = {
0};
// 特殊符号'\'在程序中需要转义
std::string regex =