热门标签 | HotTags
当前位置:  开发笔记 > 编程语言 > 正文

C/C++高效的正则表达式库PCRE/PCRE++

深入浅出CC中的正则表达式库(三)——PCRE,PCRE2010年4月5日小武哥发表评论阅读评论写在前面:本文是《深入浅出CC中的正则表达式库》系列的第三篇ÿ

深入浅出C/C++中的正则表达式库(三)——PCRE, PCRE++


2010年4月5日 小武哥 发表评论 阅读评论


写在前面:本文是《深入浅出C/C++中的正则表达式库》系列的第三篇,本文的主要内容是介绍PCRE和PCRE++,因为它们两个是很有渊源的,所以放在一起讲。

1. 什么是PCRE? 什么是PCRE++?
PCRE,全称是Perl Compatible Regular Expressions。从名字我们可以看出PCRE库是与Perl中正则表达式相兼容的一个正则表达式库。PCRE是免费开源的库,它是由C语言实现的,这里是它的官方主页:http://www.pcre.org/,感兴趣的朋友可以在这里了解更多的内容。
要得到PCRE库,可以从这里下载:http://sourceforge.net/projects/pcre/files/

PCRE++是一个对PCRE库的C++封装,它提供了更加方便、易用的C++接口。这里是它的官方主页:http://www.daemon.de/PCRE,感兴趣的朋友可以在这里了解更多的内容。
要得到PCRE++库,可以从这里下载:http://www.daemon.de/PcreDownload

2. PCRE接口介绍
(1). pcre_compile

1
2
3
4
5
6
7
8
9
10

pcre *pcre_compile(const char *pattern, int options,
const char **errptr, int *erroffset,
const unsigned char *tableptr);
功能:编译指定的正则表达式
参数:pattern, 输入参数,将要被编译的字符串形式的正则表达式
options
, 输入参数,用来指定编译时的一些选项
errptr
, 输出参数,用来输出错误信息
erroffset
, 输出参数,pattern中出错位置的偏移量
tableptr
, 输入参数,用来指定字符表,一般情况用NULL, 使用缺省的字符表
返回值:被编译好的正则表达式的pcre内部表示结构

(2). pcre_exec

1
2
3
4
5
6
7
8
9
10
11
12
13

int pcre_exec(const pcre *code, const pcre_extra *extra,
const char *subject, int length, int startoffset,
int options, int *ovector, int ovecsize);
功能:用来检查某个字符串是否与指定的正则表达式匹配
参数: code, 输入参数,用pcre_compile编译好的正则表达结构的指针
extra
, 输入参数,用来向pcre_exec传一些额外的数据信息的结构的指针
subject
, 输入参数,要被用来匹配的字符串
length
, 输入参数, 要被用来匹配的字符串的指针
startoffset
, 输入参数,用来指定subject从什么位置开始被匹配的偏移量
options
, 输入参数, 用来指定匹配过程中的一些选项
ovector
, 输出参数,用来返回匹配位置偏移量的数组
ovecsize
, 输入参数, 用来返回匹配位置偏移量的数组的最大大小
返回值:匹配成功返回非负数,匹配返回负数

3. PCRE++接口介绍
PCRE++把PCRE库封装成了两个类,一个是RE_Options, 用来指定匹配选项,一个是RE,用来提供匹配相关的接口。RE_options类在这里我就不介绍了,我主要介绍一下RE类:
(1)RE的构造函数传入正则表达式,并在构造函数中调用Init函数,将该正则表达进行编译
(2)RE的pattern()成员用来得到初始传入的正则表达式字符串
(3)RE的error()成员用来得到匹配过程中的出错信息
(4)RE的FullMatch()成员用来判断某字符串整体是否匹配指定正则表达式
(5)RE的PartialMatch()成员用来判断某字符串的部分是否匹配指定正则表达式

4. PCRE/PCRE++使用注意事项
(1)使用pcre请包含pcre.h头文件
(2)使用pcre_compile, pcre_exec后,记得调用pcre_free释放内存,以免造成内存泄露
(3)使用pcre编译的时候需要依赖libpcre.a
(4)使用pcre++请包含pcrecpp.h头文件
(5)使用pcre++,RE类的析构函数会自动释放相关内存,因此不用担心内存泄露
(6)使用pcre++编译的时候需要依赖libpcrecpp.a
(7)使用pcrecpp要使用pcrecpp命名空间

5. PCRE使用举例
下面是例程:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35

#include <pcre .h>
#include <stdio .h>
#include <string .h>
int main(int argc, char ** argv)
{
if (argc !&#61; 3)
{
printf("Usage: %s pattern text\n", argv[0]);
return 1;
}
const char * pPattern &#61; argv[1];
const char * pText &#61; argv[2];
const char * pErrMsg &#61; NULL;
pcre
* pPcre &#61; NULL;
int nOffset &#61; -1;
if (NULL &#61;&#61; (pPcre &#61; pcre_compile(pPattern, 0, &pErrMsg, &nOffset, NULL)))
{
printf("ErrMsg&#61;%s, Offset&#61;%d\n", pErrMsg, nOffset);
return 1;
}
else
{
if (pcre_exec(pPcre, NULL, pText, strlen(pText), 0, 0, NULL, 0) < 0)
{
printf("%s doesn&#39;t match %s\n", pText, pPattern);
}
else
{
printf("%s matches %s\n", pText, pPattern);
}
}
}

下面是运行结果&#xff1a;

1
2
3
4
5
6

wuzesheng&#64;wuzesheng-ubuntu:~/Program$ !g&#43;&#43;
g
&#43;&#43; -lpcre TestPcre.cpp -o pcre
wuzesheng&#64;wuzesheng
-ubuntu:~/Program$ ./pcre "http:\/\/.*\.qq\.com" "http://www.qq.com"
http
://www.qq.com matches http:\/\/.*\.qq\.com
wuzesheng&#64;wuzesheng
-ubuntu:~/Program$ ./pcre "http:\/\/.*\.qq\.com" "http://www.qqq.com"
http
://www.qqq.com doesn&#39;t match http:\/\/.*\.qq\.com

6. PCRE&#43;&#43;使用举例
下面是例程&#xff1a;

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25

#include
#include <pcrecpp .h>
int main(int argc, char ** argv)
{
if (argc !&#61; 3)
{
std
::cerr < < "Usage: " << argv[0] << " pattern text\n";
return 1;
}
pcrecpp
::RE oPattern(argv[1]);
if (oPattern.FullMatch(argv[2]))
{
std
::cout << argv[2] << " fully matches " << argv[1] << "\n";
}
else if (oPattern.PartialMatch(argv[2]))
{
std
::cout << argv[2] << " partially matches " << argv[1] << "\n";
}
else
{
std
::cout << argv[2] << " dose not match " << argv[1] << "\n";
}
}

下面是运行结果&#xff1a;

1
2
3
4
5
6
7
8
9

wuzesheng&#64;wuzesheng-ubuntu:~/Program$ g&#43;&#43; TestPcreCpp.cpp -lpcrecpp -o pcrecpp
wuzesheng&#64;wuzesheng
-ubuntu:~/Program$ ./pcrecpp
Usage: ./pcrecpp pattern text
wuzesheng&#64;wuzesheng
-ubuntu:~/Program$ ./pcrecpp "http:\/\/.*\.qq\.com" "http://www.qq.com"
http
://www.qq.com fully matches http:\/\/.*\.qq\.com
wuzesheng&#64;wuzesheng
-ubuntu:~/Program$ ./pcrecpp "http:\/\/.*\.qq\.com" "http://www.qq.comiii"
http
://www.qq.comiii partially matches http:\/\/.*\.qq\.com
wuzesheng&#64;wuzesheng
-ubuntu:~/Program$ ./pcrecpp "http:\/\/.*\.qq\.com" "http://www.qqq.comiii"
http
://www.qqq.comiii dose not match http:\/\/.*\.qq\.com

以上即是关于PCRE和PCRE&#43;&#43;库介绍的全部内容&#xff0c;由于内容比较多&#xff0c;我只介绍了一些关键的接口及其用法&#xff0c;如果读者朋友想更加深入的了解其它的接口&#xff0c;可以参考我上面提到的官方网站&#xff0c;另外linux下的manual也是很好的参考资料。在shell下执行man pcre和man pcrecpp便可得到很详细的资料。


推荐阅读
  • 本文详细解析了使用C++实现的键盘输入记录程序的源代码,该程序在Windows应用程序开发中具有很高的实用价值。键盘记录功能不仅在远程控制软件中广泛应用,还为开发者提供了强大的调试和监控工具。通过具体实例,本文深入探讨了C++键盘记录程序的设计与实现,适合需要相关技术的开发者参考。 ... [详细]
  • 开发笔记:实现1353表达式中的括号匹配(栈的应用) ... [详细]
  • 本文详细解析了 Android 系统启动过程中的核心文件 `init.c`,探讨了其在系统初始化阶段的关键作用。通过对 `init.c` 的源代码进行深入分析,揭示了其如何管理进程、解析配置文件以及执行系统启动脚本。此外,文章还介绍了 `init` 进程的生命周期及其与内核的交互方式,为开发者提供了深入了解 Android 启动机制的宝贵资料。 ... [详细]
  • Java Socket 关键参数详解与优化建议
    Java Socket 的 API 虽然被广泛使用,但其关键参数的用途却鲜为人知。本文详细解析了 Java Socket 中的重要参数,如 backlog 参数,它用于控制服务器等待连接请求的队列长度。此外,还探讨了其他参数如 SO_TIMEOUT、SO_REUSEADDR 等的配置方法及其对性能的影响,并提供了优化建议,帮助开发者提升网络通信的稳定性和效率。 ... [详细]
  • 题目解析给定 n 个人和 n 种书籍,每个人都有一个包含自己喜好的书籍列表。目标是计算出满足以下条件的分配方案数量:1. 每个人都必须获得他们喜欢的书籍;2. 每本书只能分配给一个人。通过使用深度优先搜索算法,可以系统地探索所有可能的分配组合,确保每个分配方案都符合上述条件。该方法能够有效地处理这类组合优化问题,找到所有可行的解。 ... [详细]
  • 在C++程序中,文档A的每一行包含一个结构体数据,其中某些字段可能包含不同数量的数字。需要将这些结构体数据逐行读取并存储到向量中,随后不仅在控制台上显示,还要输出到新创建的文档B中。希望得到指导,感谢! ... [详细]
  • 在C语言中,指针的高级应用及其实例分析具有重要意义。通过使用 `&` 符号可以获取变量的内存地址,而 `*` 符号则用于定义指针变量。例如,`int *p;` 定义了一个指向整型的指针变量 `p`。其中,`p` 代表指针变量本身,而 `*p` 则表示指针所指向的内存地址中的内容。此外,指针在不同函数中可以具有相同的变量名,但其作用域和生命周期会有所不同。指针的灵活运用能够有效提升程序的效率和可维护性。 ... [详细]
  • 在使用 Qt 进行 YUV420 图像渲染时,由于 Qt 本身不支持直接绘制 YUV 数据,因此需要借助 QOpenGLWidget 和 OpenGL 技术来实现。通过继承 QOpenGLWidget 类并重写其绘图方法,可以利用 GPU 的高效渲染能力,实现高质量的 YUV420 图像显示。此外,这种方法还能显著提高图像处理的性能和流畅性。 ... [详细]
  • 在C语言程序开发中,调试和错误分析是确保代码正确性和效率的关键步骤。本文通过一个简单的递归函数示例,详细介绍了如何编写和调试C语言程序。具体而言,我们将创建一个名为 `factorial.c` 的文件,实现计算阶乘的功能,并通过逐步调试来分析和解决可能出现的错误。此外,文章还探讨了常见的调试工具和技术,如GDB和断点设置,以帮助开发者高效地定位和修复问题。 ... [详细]
  • 题目要求维护一个数列,并支持两种操作:一是查询操作,语法为QL,用于查询数列末尾L个数中的最大值;二是更新操作,用于修改数列中的某个元素。本文通过ST表(Sparse Table)优化查询效率,确保在O(1)时间内完成查询,同时保持较低的预处理时间复杂度。 ... [详细]
  • PHP预处理常量详解:如何定义与使用常量 ... [详细]
  • 本文详细介绍了一种利用 ESP8266 01S 模块构建 Web 服务器的成功实践方案。通过具体的代码示例和详细的步骤说明,帮助读者快速掌握该模块的使用方法。在疫情期间,作者重新审视并研究了这一未被充分利用的模块,最终成功实现了 Web 服务器的功能。本文不仅提供了完整的代码实现,还涵盖了调试过程中遇到的常见问题及其解决方法,为初学者提供了宝贵的参考。 ... [详细]
  • 在2019年寒假强化训练中,我们深入探讨了二分算法的理论与实践应用。问题A聚焦于使用递归方法实现二分查找。具体而言,给定一个已按升序排列且无重复元素的数组,用户需从键盘输入一个数值X,通过二分查找法判断该数值是否存在于数组中。输入的第一行为一个正整数,表示数组的长度。这一训练不仅强化了对递归算法的理解,还提升了实际编程能力。 ... [详细]
  • 本文深入解析了 Kuangbin 数学训练营中的经典问题——Ekka Dokka,并通过详细的代码示例和数学推导,探讨了该问题的多种解法及其应用场景。通过对算法的优化和扩展,本文旨在为读者提供全面的理解和实用的参考。 ... [详细]
  • 经过两天的努力,终于成功解决了半平面交模板题POJ3335的问题。原来是在`OnLeft`函数中漏掉了关键的等于号。通过这次训练,不仅加深了对半平面交算法的理解,还提升了调试和代码实现的能力。未来将继续深入研究计算几何的其他核心问题,进一步巩固和拓展相关知识。 ... [详细]
author-avatar
老薛很厚道
这个家伙很懒,什么也没留下!
PHP1.CN | 中国最专业的PHP中文社区 | DevBox开发工具箱 | json解析格式化 |PHP资讯 | PHP教程 | 数据库技术 | 服务器技术 | 前端开发技术 | PHP框架 | 开发工具 | 在线工具
Copyright © 1998 - 2020 PHP1.CN. All Rights Reserved | 京公网安备 11010802041100号 | 京ICP备19059560号-4 | PHP1.CN 第一PHP社区 版权所有