正则表达式在字符串处理中的应用_《草根》第2期_第1页
正则表达式在字符串处理中的应用_《草根》第2期_第2页
正则表达式在字符串处理中的应用_《草根》第2期_第3页
正则表达式在字符串处理中的应用_《草根》第2期_第4页
正则表达式在字符串处理中的应用_《草根》第2期_第5页
已阅读5页,还剩3页未读 继续免费阅读

下载本文档

版权说明:本文档由用户提供并上传,收益归属内容提供方,若内容存在侵权,请进行举报或认领

文档简介

1、正则表达式在字符串处理中的应用/*编程技术*/作者 高洛峰初次接触正则表达式的人除了感觉它有些繁琐外,还会有一种深不可测的感觉。其实正则表达式就是描述字符排列模式的一种自定义的语法规则,在PHP给我们提供的系统函数中,使用这种模式对字符串进行匹配、查找、替换及分割等操作,它的应用非常广泛。例如,常见的使用正则表达式去验证用户在表单中提交的用户名、密码、E-mail地址、身份证号码及电话号码等格式是否合法;在用户发布文章时,将输入有URL的地方全部加上对应的链接;按所有标点符号计算文章中一共有多少个句子;抓取网页中某种格式的数据等等。正则表达式并不是PHP自己的产物,在很多领域都会见到它的应用,

2、除了在Perl、C#及JAVA语言中应用外,在我们的B/S架构软件开发中,Linux操作系统、前台JavaScript脚本、后台脚本PHP以及MySQL数据库中都可以应用到正则表达式。正则表达式简介/a-zA-z+:/s*/ /匹配网址URL的正则表达式/<(S*?)>*>.*?</1>|<.*? />/i /匹配HTML标记的正则表达式/w+(-+.w+)*w+(-.w+)*.w+(-.w+)*/ /匹配Email地址的正则表达式正则表达式也称为模式表达式,自身具有一套非常完整的、可以编写模式的语法体系,提供了一种灵活且直观的字符串处理方法。正则表达

3、式通过构建具有特定规则的模式,与输入的字符串信息比较,从而实现字符串的匹配、查找、替换及分割等操作。下例中给出了3个模式,都是按照正则表达式的语法规则构建的。如下所示:不要被上例中看似乱码的字符串给吓退,它们就是按照正则表达式的语法规则构建的模式,是一种由普通字符和具有特殊功能的字符组成的字符串。而且要将这些模式字符串,放在特定的正则表达式函数中使用才有效果。学完本文以后就可以自由应用这样的代码了。在PHP中支持两套正则表达式的处理函数库。一套是由PCRE(Perl Compatible Regular Expression)库提供的,与Perl语言兼容的正则表达式函数。使用“preg_”为前

4、缀命名的函数,而且表达式都应被包含在定界符中,如斜线(/)。另一套是由POSIX(Portable Operation System interface)扩展语法的正则表达式函数,使用以“ereg_”为前缀命名的。两套函数库的功能相似,执行效率稍有不同。一般而言,实现相同的功能,使用第一种PCRE库提供的正则表达式效率略占优势。所以在本文中主要介绍使用“preg_”为前缀命名的正则表达式函数,如表1所示:表1 与Perl语言兼容的正则表达式处理函数函数名功能描述preg_match()进行正则表达式匹配preg_match_all()进行全局正则表达式匹配preg_replace()执行正则表

5、达式的搜索和替换preg_split()用正则表达式分割字符串preg_grep()返回与模式匹配的数组单元preg_replace_callback()用回调函数执行正则表达式的搜索和替换正则表达式的语法规则/<a.*?(?: |t|r|n)?href='"?(.+?)'"?(?:(?: |t|r|n)+.*?)?>(.+?)</a.*?>/sim/获取链接地址正则表达式描述了一种字符串匹配的模式,通过这个模式在特定的函数中对字符串进行匹配、查找、替换及分割等操作。正则表达式作为一个匹配的模板,是由原子(普通字符,例如字符a到z)、

6、有特殊功能的字符(称为元字符,例如*、+和?等)以及模式修正符三部分组成的文字模式。一个最简单的正则表达式模式中,至少也要包含一个原子,如“/a/”。而且在与Perl兼容的正则表达式函数中使用模式时,一定要给模式加上定界符,即将模式包含在两个反斜线“/”之间。一个HTML链接地址的正则表达式模式如下所示:在网页中任何属于HTML有效的链接标签,都可以和这个正则表达式的模式匹配上。该模式就用到了编写正则表达式模板的原子、元字符和模式休正符三个组成部分,将其拆分后如下所示:¨ 定界符是使用的是两个反斜线“/”,将模式放在它之间声明¨ 原子用到了<、a、href、=、

7、9;、"、/、>等普通字符和t、r、n等转义字符¨ 元字符使用了、()、|、.、?、*、+等具有特殊含义的字符¨ 用到的模式修正符是在定界符最后一个反斜线之后的三个字符“s”、“i”和“m”<?php$pattern='/<a.*?(?: |t|r|n)?href='"?(.+?)'"?(?:(?: |t|r|n)+.*?)?>(.+?)</a.*?>/sim'$content="请进单击进入<a href=''>LAMP兄弟连</a

8、>技术社区。"if(preg_match($pattern, $content) /使用preg_match()函数进行正则表达式的模式匹配echo "成功匹配,在第二个参数中包含有效的HTML链接标签字符串。" else echo "在第二个参数的字符串中搜索不到有效的HTML链接标签。" ?>对于原子、元字符以及模式修正符的使用将在后面详细介绍。首先编写一个示例,了解一下正则表达式的应用。通过PHP中给我们提供的preg_match()函数,使用上例中定义的正则表达式模式。该函数有两个必选参数,第一个参数需要提供用户编写的正则表

9、达式模式,第二个参数需要一个字符串。该函数的作用就是在第二个字符串参数中,搜索与第一个参数给出的正则表达式匹配的内容。如果匹配成功则返回真。代码如下所示:在上面的代码中,使用正则表达式的语法规则,定义一个匹配HTML中链接标签的模式并存放在变量$pattrn中。又定义了一个字符串变量$content,在字符串中如果包含有效的HTML链接标签,则使用preg_match()函数时,就可以按$pattrn模式所定义的格式搜索到链接标签。Ø 定界符/</w+>/ /使用反斜线作为定界符号合法|(d3)-d+|Sm /使用竖线“”作为定界符号合法!(?i)php34! /使用感叹

10、号“!”作为定界符号合法s+(s+)?$ /使用花括号“”作为定界符号合法/href='(.*)' /非法定界符号,缺少结束定界符 1-d3-d3-d4| /非法定界符号,缺少起始定界符在程序语言中,使用与Perl兼容的正则表达式,通常都需要将模式表达式放入定界符之间。作为定界的字符也不仅仅局限于使用反斜线“/”。除了字母、数字和正斜线“”以处的任何字符都可以作为定界符号,例如“#”、“!”、“”和“”等都是可以的。通常习惯都将模式表达式包含在两个反斜线“/”之间。下例是一些模式表达式的应用,如下所示:Ø 原子原子是正则表达式的最基本的组成单位,而且在每个模式中最少要

11、包含一个原子。原子是由所有那些未显式指定为元字符的打印和非打印字符组成,包括所有的大写和小写字母字符、所有数字、所有标点符号以及一些其它符号。例如az、AZ、09、双引号“”、单引号“”等。还包括一些非打印字符,如表2所示列出了正则表达式中常用的非打印字符及其含义:表2 正则表达式中常用的非打印字符原子字符含义描述cx匹配由x指明的控制字符。例如,cM匹配一个Control-M或回车符。x的值必须为A-Z或a-z之一。否则,将c视为一个原义的'c'字符。f匹配一个换页符。等价于x0c和cL。n匹配一个换行符。等价于x0a和cJ。r匹配一个回车符。等价于x0d和cM。s匹配任何空

12、白字符,包括空格、制表符、换页符等等。等价于fnrtv。S匹配任何非空白字符。等价于fnrtv。t 匹配一个制表符。等价于x09和cI。v匹配一个垂直制表符。等价于x0b和cK。Ø 元字符利用Perl正则表达式还可以做另一件有用的事情,这就是使用各种元字符来搜索匹配。所谓元字符,就是用于构建正则表达式的具有特殊含义的字符,例如的“*”、“+”、“?”等。如果要在正则表达式中包含元字符本身,使其失去特殊的含义则必须在前面加上“”进行转义。正则表达式有以下特殊字符,如表3所示:表3 正则表达式的元字符元字符含义描述d匹配任意一个十进制数字,等价于0-9D匹配任意一个除十进制数字

13、以外的字符,等价于0-9s匹配任意一个空白字符,等价于fnrtvS匹配除空白字符以外任何一个字符,等价于fnrtvw匹配任意一个数字、字母或下划线,等价于0-9a-zA-Z_W匹配除数字、字母或下划线以外的任意一个字符,等价于0-9a-zA-Z_*匹配0次、1次或多次其前的原子+匹配1次或多次其前的原子?匹配0次或1次其前的原子.匹配除了换行符外的任意一个字符|匹配两个或多个分支选择n表示其前面的原子恰好出现n次n, 表示其前面的原子出现不少于n次n, m表示其前面的原子至少出现n次,最多出现m次或A匹配输入字符串的开始位置(或在多行模式下行的开头,即紧随一换行符之后)$或Z匹配输入字符串的结

14、束位置(或在多行模式下行的结尾,即紧随一换行符之前)b匹配单词的边界B匹配除单词边界以外的部分匹配方括号中指定的任意一个原子匹配除方括号中的原子以外的任意一个字符()匹配其整体为一个原子,即模式单元。可以理解为由多个单个原子组成的大原子构造正则表达式的方法和创建数学表达式的方法相似,就是用多种元字符与操作符将小的表达式结合在一起来创建更大的表达式。正则表达式的组件可以是单个的字符、字符集合、字符范围、字符间的选择或者所有这些组件的任意组合。元字符是组成正则表达式的最重要部分,下面将这些元字符分为几类分别讲解。Ø 通用字符类型/0-9a-ZA-Z_+0-9a-ZA-Z_+(.0-9a-

15、ZA-Z_+)0,3$/ /E-mail的正则表达式模式/w+w+(.w+)0,3$/ /同上通用字符类型可以匹配相应类型中的一个字符,例如“d”可以匹配数字类型中的任意一个十进制数字。共有6种通用字符类型,包括“d”和“D”、“s”和“S”、“w”和“W”。当然也可以使用原子表制定出这种通用字符类型,例如0-9和“d”的功能一样,都可以匹配一个十进制数字。但使用通用字符类型要方便得多,如下所示:上面两个正则表达式的模式作用一样,都是匹配电子邮件的格式。很显然使用通用字符类型“w”要比使用原子表“0-9a-zA-Z_”的格式清晰得多。Ø 限定符/as*b/ /“s”表示空白原子,可以

16、匹配在a和b之间没有空白、一个或有多个空白情况/ad+b/ /可以匹配在a和b之间有一个或有多个数字的情况,如a2b、a34567b等/aW?b/ /可以匹配在a和b之间有一个或有没有特殊字符,如ab、a#b、a%b等/ax4b/ /可以匹配在a和b之间必须有4个x的字符串,如axxxxb/ax2,b/ /可以匹配在a和b之间至少要有2个x的字符串,如axxb、axxxxxxb等/ax2,4b/ /可以匹配在a和b之间至少有2个和最多有4个x的字符串,如axxb、axxxb和axxxxb限定符用来指定正则表达式的一个给定原子必须要出现多少次才能满足匹配。有“*”、“+”、“?”、“n”、“n,

17、”以及“n,m”共6种限定符,他们之间的区别主要是重复匹配的次数不同。其中“*”、“+”和“n, ”限定符都是贪婪的,因为它们会尽可能多的匹配文字。如下所示:元字符“*”表示0次、1次或多次匹配其前的原子,也可以使用“0,”完成同样的匹配。同样“+”可以使用“1,”表示,以及“?”可以使用“0,1”表示。Ø 边界限制/this/ /匹配此字符串是否是以字符串“this”开始的,匹配成功/test$/ /匹配此字符串是否是以字符串“test”结束的,匹配成功/bisb/ /匹配此字符串中是否含有单词“is”,因为在字符串“is”两边都需要有边界/Bisb/ /查找字符串“is”时,左边

18、不能为边界而右边必须有边界,如“this”匹配成功用来限定字符串或单词的边界范围,以获得更准确的匹配结果。元字符“”(或“A”)和“$”(或“Z”)分别指字符串的开始与结束,而“b”用于描述字符串中每个单词的前或后边界,与之相反的元字符“B”表示非单词边界。例如有一个字符串“this is a test”使用的边界限制如下所示:Ø 句号(.)/a.b/ /可以匹配在a和b之间有任意一个字符的字符串,例如axb、ayb、azb等在字符类之外,模式中的圆点可以匹配目标中的任何一个字符,包括不可打印字符。但不匹配换行符(默认情况下),相当于“n”(Unix系统)或“rn”(Windows系

19、统)。如果设定了模式修正符号“s”则圆点也会匹配换行符。处理圆点与处理音调符“”和美元符“$”是完全独立的,唯一的联系就是它们都涉及到换行符。如下所示:通常,可以使用“.*?”或“.+?”组合来匹配除换行符以外的任何字符串。例如,模式“/<b>.*?b</b>/”可以匹配以“<b>”标签开始,“</b>”标签结束的任何不包括换行符的字符串。Ø 模式选择符()竖线字符“”用来分隔多选一模式,在正则表达式中匹配两个或更多的选择之一。例如,模式“LAMP|J2EE”表示可以匹配“LAMP”也可以匹配“J2EE”,因为元字符竖线“”的优先级是最

20、低的,所以并不是表示匹配“LAMP2EE”或“LAMPJ2EE”。也可以有更多的选择,例如模式“/Linux|Apache|MySQL|PHP/”表示可以从中任意匹配一组。Ø 原子表()/apjsp/ /可以匹配asp、psp或jsp三种,从原子表中仅选择一个原子使用原子表“”可以定义一组彼此地位平等的原子,且从原子表中仅选择一个原子进行匹配。如下所示:/apjsp/ /可以匹配除了asp、php或jsp三种以外的字符串,如xsp、ysp或zsp等还可以使用原子表“”匹配除表内原子外的任意一个字符,通常称为排除原子表。如下所示:/0xX0-9a-fA-F+/ /可以匹配一个简单的十六

21、进制数,如0x2f、0X3AE或0x4aB等另外,在原子表中可以使用负号“-”连接一组按ASCII码顺序排列的原子,能够简化书写。如下所示:Ø 模式单元/(very )*good/ /可以匹配good、very good、very very good或very very good等模式单元是使用元字符“()”将多个原子组成大的原子,被当作一个单元独立使用。与数学表达式中的括号作用类似,一个模式单元中的表达式将被优先匹配。如下所示:在上面的例子中,紧接着“*”前的多个原子“very”用元字符“()”括起来被当作一个单元,所以原子“(very)”可以没有,也可以有一个或多个。Ø

22、 后向引用/d4Wd2Wd2$/ /这是一个匹配日期的格式,如2008-08/08或2008/08-08等'/d4(W)d21d2$/ /这是一个匹配日期的格式,如2008-08-08或2008/08/08等使用元字符“( )”标记的开始和结束多个原子,不仅是一个独立的单元,也是一个子表达式。这样,对一个正则表达式模式或部分模式两边添加圆括号将导致相关匹配存储到一个临时缓冲区中,可以被获取供以后使用。所捕获的每个子匹配都按照在正则表达式模式中从左至右所遇到的内容存储。存储子匹配的缓冲区编号从1开始,连续编号直至最大99个子表达式。每个缓冲区都可以使用“n”访问,其中n为一个标识特定缓冲

23、区的一位或两位十进制数。例如“1”、“2”、“3”等的形式进行引用,在正则表达的模式中使用时还需要在前面再加上一个反斜线,将斜线再次转义。例如“1”、“2”、“3”等。如下所示:在上例中声明了两个正则表达式,用来匹配日期格式。如果使用第一种模式则在年、月及日之间的分隔符号可以是任意的特殊字符,完全可以不对应。但实际应用中日期格式之间的分隔符号必须是对应的,即年和月之间使用“-”,则月和日之间也要和前面的一样使用“-”。在上述中的第二个正则表达式就可以达到这种效果。这是因为模式“W”加上了元字符括号“()”,结果已经被存储到缓冲区中。所以在第一个“(W)”的位置使用“-”则下一个位置使用“1”引

24、用时,其匹配模式也必须是字符“-”。/(Windows)(Linux)2OS/ /使用“2”再次引用第二个缓冲区中的字符串“Linux”/(?:Widows)(Linux)1OS/ /使用“?:”忽略了第一个子表式的存储,所以“1”引用的就是“Linux”如需要使用模式单元而又不想存储匹配结果时,可以使用非捕获元字符 “?:”、“?=”或“?!'”来忽略对相关匹配的保存。在一些正则表达式中,使用非存储模式单元是必要的,可以改变其后向引用的顺序。如下所示:Ø 模式匹配的优先级在使用正则表达式时,需要注意匹配的顺序。通常相同优先级是从左到右进行运算,不同优先级的运算先高后低。各种

25、操作符的匹配顺序优先级从高到低如表4所示:表4 模式匹配的顺序顺 序元字符描 述1转义符号2()、(?:)、(?=),、模式单元和原子表3*、+、?、n、n,、n,m重复匹配4、$、b、B、A、Z边界限制5|模式选择Ø 模式修正符模式修正符号在正则表达式定界符之外使用(最后一个反斜线“/”之后),例如“/php/i”。其中“/php/”是一个正则表达式的模式,而“i”就是修正此模式所使用的修正符号,用来在匹配时不区分大小写。模式修正符可以调整正则表达式的解释,扩展了正则表达式在匹配、替换等操作时的某些功能,而且模式修正符号也可以组合使用,更增强了正则表达式的处理能力。例如“/php/Uis”则是使用“U”、“i”和“s”三个模式修正符组合在一起使用。模式修正符对编写简洁而简小的表达式大有帮助,在下面的表格中,列出了一些常用的模式修正符及其功能说明。如表5所示:表5 模式修正符号模式修正符功能描述i在和模式进行匹配时不区分大小写m将字符串视为多行。默认的正则开始“”和结束“$”将目标字符串作为单一的一“行”字符(甚至其中包含有换行符也是如此)。如果在修饰符中加上“m”,那么开始和结束将会指字符串的每一行,每一行的开头就是“”,结尾就是“$”。s如果设定了此修正符,模式中的圆点元

温馨提示

  • 1. 本站所有资源如无特殊说明,都需要本地电脑安装OFFICE2007和PDF阅读器。图纸软件为CAD,CAXA,PROE,UG,SolidWorks等.压缩文件请下载最新的WinRAR软件解压。
  • 2. 本站的文档不包含任何第三方提供的附件图纸等,如果需要附件,请联系上传者。文件的所有权益归上传用户所有。
  • 3. 本站RAR压缩包中若带图纸,网页内容里面会有图纸预览,若没有图纸预览就没有图纸。
  • 4. 未经权益所有人同意不得将文件中的内容挪作商业或盈利用途。
  • 5. 人人文库网仅提供信息存储空间,仅对用户上传内容的表现方式做保护处理,对用户上传分享的文档内容本身不做任何修改或编辑,并不能对任何下载内容负责。
  • 6. 下载文件中如有侵权或不适当内容,请与我们联系,我们立即纠正。
  • 7. 本站不保证下载资源的准确性、安全性和完整性, 同时也不承担用户因使用这些下载资源对自己和他人造成任何形式的伤害或损失。

评论

0/150

提交评论