首页 > 代码库 > 正则表达式(一)——基本介绍
正则表达式(一)——基本介绍
正则表达式是干什么的
其实正则表达式的本质就四个字“处理信息”。它并不是一个简简单单的组织字符串的工具,也不只是编程的一种工具,它除了应用于编程语言中,也广泛应用于各类文本编辑器中,例如Unix/Linux的vi,Windows上的EmEditor、EditPlus,包括word中,也可以使用一些常用的正则表达式进行搜索,替换。
历史发展
我觉得在学习一门新知识之前,先了解它的历史,是很有必要的。通过了解它的发展,完善的过程,可以更好的去理解它为什么会这样,为什么要这样,为什么成了这样。
------------20世纪40年代------------
提出正则表达式的最初想法的人是两个"神经学家",他们认为大脑的神经系统的神经元层面就是这样工作的,所以正则表达式可以被看作是一种模拟大脑模型。
------------20世纪50~60年代------------
理论数学界给这个模型起了一个名字,叫做“正则集合”。然后斯蒂芬·科尔·克莱尼(一个数学家)发明了一套表示这个正则集合的方法,就是我们今天看到的“正则表达式”。
------------1968年------------
Ken Thompson在1968年的时候把这个“正则表达式”的理论成果用于做一些搜索算法的研究,他描述了一种正则表达式的编译器,于是出现了应该算是最早的正则表达式的编译器qed。然后qed这个编译器就出现在了unix中,发展到后来,就成了ed编辑器;再后来,又发展成了grep编辑器;现在,则又添加了egrep编辑器。Ken Thompson同时也是Unix的主要发明人。
在这之后,正则表达式不断的发展壮大,然后大规模应用于各种领域,根据这些领域各自的条件需要,又发展出了许多版本的正则表达式,出现了许多的分支。我们称这些分支叫做“流派”。
------------1968年~1985年------------
这一段时期,是正则表达式的各个流派百家齐鸣的时期。grep进化了,比以往加入了更多的元字符的支持,修正了一些匹配模式上的问题。此时egrep诞生了,他两都出生于大名鼎鼎的贝尔实验室,egrep展现了现如今所使用的大部分“元字符”,比起grep,egrep加上了一些“量词”,入+、?之类,还允许量词作用于括号中的表达式,加入了多选结构。总之,egrep就可以算是现在大多数流派的鼻祖,现在大不多流派最基本的正则表达式的内容,就是egrep当初的内容。
在一段时期,发展的不止grep,也包括awk、lex、sed这些编程语言。各个流派互相借鉴,各自发展,借鉴别人的功能,不好使又删了,也没留下文档。然后就出现了许多大体看上去差不多,但细微之处不同的正则表达式工具。众多的流派对正则表达式支持的不一致,给使用者带来了一些麻烦,这个麻烦直到今天还存在。
------------1986年------------
乱世过去了,朝廷就要出来一统天下了,于是1986年诞生了POSIX标准。这个标准的制定确保了操作系统之间的移植性(这个标准是针对操作系统的,不是只针对正则表达式)。POSIX的正则表达式部分把常见的各种流派分成了两部分“Basic Regular Expressions(BREs)”和"Extended Regular Expressions(EREs)"。非正规的,可以简单的理解为,BREs就是grep包括它的延续。EREs就是egrep包括它的延续。
1986年,在正则表达式界,还发生了一件重要的事情。一个叫Henry Spencer的人,发布了他用C语言写的正则表达式包,这个包可以毫无困难的植入其他程序。每个使用这个包的开发者,都可以单独算作一个流派。这在当时属于一个开创性的事件。到现在,也有一些正则表达式引擎的开发者,是基于这个包完成的。
------------1987年~后来------------
1987年12月,perl诞生了,这对于正则表达式界来说,很重要。它综合了其他的语言,用正则表达式作为基础,开创了一个新的流派,perl流派。perl的重要意义在于,它发展到后来,开始了一个对于正则表达式的整合。现在我们使用的大部分编程语言,Tcl、java、Ruby、.Net、PHP、C/C++、python。它们都有自己的正则表达式的包,但,它们都会说自己“兼容perl”。perl语言发展到perl5的时候,开始成为一种制作网页的流行的语言,原因在于web页的生成就是文本的处理,而perl发明的初衷刚好也是文本的处理。所以perl也广受欢迎。perl的语言当中融入了正则表达式,它并不像其他的语言一样,使用正则表达式需要额外的编译、引入包。例如:
if($text =~ m/^abc:(.*)/i){do something}
下划线的部分,即/和/中间的部分,就是正则表达式。
正则表达式的发展到现阶段,对于正则表达式的引擎来说,总共分为3类:“传统NFA”、“POSIX NFA”、 “DFA”。上述所有加粗的名词,此文暂时不涉及对它们的解释,请自行搜索。
正则表达式的思维模式
现在就说正则表达式的思维模式可能为时尚早,但我觉得有必要提一提。在了解一人之前,你要了解它的思维模式,才能更好的和他沟通。正则表达式的思维模式,就是正则表达式的本质,就是正则表达式的原理,就是正则表达式的引擎运行流程。
我们要这样来看一个正则表达式:按字符依次匹配。
以一个最简单的正则表达式作为例子: 正则(dinner),文本(Bod has dinner)
匹配的流程就大概是这样:取出正则中的‘d’字母与文本中的第一个单词‘B’进行匹配,不匹配。文本中移到下一位‘o’,‘d’与‘o’进行匹配,不匹配,继续。循环直到文本中移动到字母‘d’,匹配,正则中移动到‘i’字母,与文本中的‘i’字母进行匹配,不匹配。正则回到字母‘d’, 如此循环,最后到正则完的时候匹配完成。
dinner | Bod has dinner → dinner | Bod has dinner → dinner | Bod has dinner→ dinner | Bod has dinner → dinner | Bod has dinner ······ → dinner | Bod has dinner → dinner | Bod has dinner → dinner | Bod has dinner ······· → dinner | Bod has dinner
就是上面这样一个过程。
正则表达式的构成
正则表达式的构成由以下几部分组成:元字符、量词、零宽断言。这3个是组成正则表达式的主要部分,有的情况下,也可以把 模式 也作为正则表达式的一部分。组成部分的内容会在后续博文中完成