【转】刨根究底正则表达式(2):文本查找方式的演化历史

上一篇文章讲到,从根源上来讲,正则表达式是为了解决文本的查找问题(也称为匹配问题)而诞生的。不过,文本查找方式的历史,要远早于正则表达式。

那么,在正则表达式出现之前,文本查找方式经历了什么演化过程呢?

最后为什么又出现了正则表达式呢?换言之,正则表达式的出现,在文本查找方面,解决了其出现之前所不能解决的什么问题呢?

接下来我们一起来寻找这些问题的答案。

直接字面查找方式

正则表达式其中最基本的功能是为了满足文本查找的需求,而文本查找需求,是一种非常基础、极为常见的需求。

很自然,最先想到和做到的当然就是直接的字面文本查找(简称字面查找)。所谓“字面文本”,指的是用于查找的文本本身就是直接要查找的文本,也就是说,用于查找的文本没有特殊含义,就表示文本本身字面上的含义。

比如要查找文本“张三”,就直接以文本“张三”去进行查找。

但有时我们的查找需求要更为复杂一些,比如不仅要查找“张三”,还有“李三”、“王三”等所有名字中含有“三”这个字的两字姓名。

这种情况下,姓名中的姓就是不确定的了,那怎么办呢?于是比直接的字面查找更为强大、更为方便的另一种查找方式出现了:间接的模式查找方式。

间接模式查找方式

这里出现了一个关键术语:模式。那什么是模式呢?

我们知道,工厂生产产品,往往需要先有产品的模板或模具。而模式,就是模板样式或模具样式。

正如符合某种样式的模板或模具,可以用来生产符合这种样式的同一类产品一样,反过来,也可以用某种样式的模板或模具,来检验框定或筛选过滤出哪些产品才是符合这种样式的同一类产品。

比如,以上面这个查找案例来说,从“张三”、“李三”、“王三”等所有名字中含有“三”这个字的两字姓名中抽取出来的查找模式可能是这样的:“?三”,其中的“?”代表所有的单姓。

(注:为简化讨论,我们这里假定用于查找的文本仅限于姓名,不包括非姓名的其他文本,比如不包括“一二三”这样的文本,而且也暂不考虑两字姓名以外的其他三字姓名、四字姓名等。)

因此,就可以用“?三”这个查找模式来筛选过滤出所有两字姓名中以“三”这个字为名字的姓名。 换句话说,只要是所有两字姓名中以“三”这个字为名字的姓名,都属于符合“?三”这个模式的同一类姓名,因此都可以通过该模式查找匹配出来。

这里,用于查找的文本模式“?三”,并不是我们要直接查找的文本本身,“?三”中的“?”并不是表示“?”这个字符的字面本身——问号字符,而是具有了特殊含义——表示所有的单姓,因而“?”在这里具有了一定程度的抽象性、代表性、通用性和普适性。

间接模式查找方式目前大致上可划分为“通配符查找方式”和“正则表达式查找方式”两种,下面分别进行简要介绍。

通配符查找方式

通配符查找方式,在操作系统的文件查找功能中使用得非常普遍。

在这种间接的模式查找方式中,通常使用到的通配符除了上面提到的?号,还有*号。

在操作系统中,一般使用?和*这两个具有抽象性、代表性和通用性的通配符来查找硬盘上的文件。其中,?通配符所规定的查找规则是查找文件名中的单个字符,而*通配符所规定的查找规则是查找文件名中的零个、一个或多个字符。

比如像“data?.dat”这样的查找模式,将可以查找到下列文件名:

data1.dat

datax.dat

dataN.dat

而像“data*.dat”这样的查找模式,则可以查找到下列文件名:

data.dat

data1.dat

data12.dat

datax.dat

dataXYZ.dat

因此,所谓“通配符”,即“通用的查找匹配字符”,就是将某些字符(比如?号和*号)规定为特殊的用于查找文本的通用字符。

用某个通用字符按事先所规定的规则来查找某些常规字符,从而实现“以一对多”(或“以一代多”)、“以简对繁”(或“以简代繁”)地进行查找。

相比较于直接的字面查找方式只能“以一对一”、“以多对多”,或者说“以简对简”、“以繁对繁”,通配符查找模式显然更加抽象化、模式化,所以也就更为通用化、普适化。

然而,尽管通配符查找方式比直接的字面查找方式更强大、更方便、更通用、更普适,但它的功能还是非常有限的,无法精确而灵活地表达更为复杂的查找条件(即查找规则)。

比如无法分组、没有分支结构(即不支持“或运算”)、不支持量词(即不支持循环)、不支持字符组等等。

比如,我们不仅要查找两字姓名中的名为“三”字的所有姓名,还要查找两字姓名中的名为“四”字的所有姓名,如果使用通配符查找方式的话,怎么办呢?

由于通配符查找方式没有分支结构,不支持或运算,即不支持类似于“?三|?四”这样的写法,则只能分两次进行查找,这显然非常不方便。

再举个例子,如果我们要查找文件系统中命名为DxxxDxxxDxxx.dat的所有文件(其中的x代表任意字符),由于通配符查找方式不支持分组和量词,也就是不支持类似于“(D?{3}){3}”这样的写法,也是相当麻烦的。

正则表达式查找方式

查找需求的多样化和复杂性,呼唤着比通配符查找方式更加强大、更加方便、更加通用、更加普适的查找方式。

于是,能够更为精确、更为灵活地表达更加复杂、更加抽象、更加通用、更加普适的查找条件的全新查找方式——正则表达式就应运而生了。

因此,站在查找方式的历史演化角度上来看,通配符查找方式可认为是正则表达式的前身,或者换言之,正则表达式是通配符查找方式的升级版。

和通配符类似,正则表达式也是以间接的模式来进行文本查找的。显然,相比较于前面所述的“直接字面查找”方式来说,通配符查找方式和正则表达式查找方式这两种以模式进行查找的方式就是“间接模式查找”方式。

比如,还是前文所述的例子,我们不仅要查找两字姓名中的名为“三”字的所有姓名,还要查找两字姓名中的名为“四”字的所有姓名,用通配符查找方式是只能分成两次进行,但如果使用正则表达式查找的话,只需查找一次,并且写法非常简洁:.三|.四,显然更为方便。

同样,如果我们要查找文件系统中命名为DxxxDxxxDxxx.dat的所有文件(其中的x代表任意字符),使用通配符查找方式的话,查找表达式写起来也是很麻烦的,但如果使用正则表达式的话,只需写作:(D.{3}){3},正则表达式的表达能力明显比通配符强得多。

显然,正则表达式查找方式相比较于通配符查找方式来说,更为淋漓尽致地体现了“以一对多”(或“以一代多”)、“以简对繁”(或“以简代繁”)的模式查找方式的特点。

这就是正则表达式​之所以被发明出来的原因。

不过,既然正则表达式更为抽象化、通用化和普适化,也更为模式化,功能也更为强大、更加灵活,当然也就更为复杂,更难以学习和掌握。

毕竟,强大灵活与简单易用,始终都是一对矛盾。

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.mzph.cn/news/437475.shtml

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈email:809451989@qq.com,一经查实,立即删除!

相关文章

正则表达式: input框禁止输入空格:不能只有空格、不能有空格、不能为空的判断

1.只有中间和最后能输入空格(如果让最后不能输入空格则把最后一个*改成),(如果想让开头可以输入空格则把改成*) ^[^\s][\s]*.*$2.不能输入空格 ^[^\s]*$3.如果也不能为空(我是用required来判断的),把*改成 (具体我没测试,感觉可以&#xff…

台式机电脑配置单_2020年电脑配置单重点硬件参考

,电脑的基本配件扫盲我前面写过很多,相信很多小伙伴都看过了,没有看过的可以上我专栏参观:电脑神棍局-组装机专栏​www.zhihu.com配置单在本文后面两篇,但是建议前面花两分钟看下。游戏篇后续还有工作和视频工作站篇主…

【转】刨根究底字符编码之五——简体汉字编码方案(GB2312、GBK等)以及全角、半角、CJK

一、概述 1. 英文字母再加一些其他标点字符之类的也不会超过256个,用一个字节来表示一个字符就足够了(2^8 256)。但其他一些文字不止这么多字符,比如中文中的汉字就多达10多万个,一个字节只能表示256个字符,肯定是不够的&#…

正则表达式:匹配Double类型,整数和小数

正则表达式:匹配Double类型,整数和小数 ^(([0])|([1-9][0-9]*.{1}[0-9])|([0].{1}[1-9][0-9]*)|([1-9][0-9]*)|([0][.][0-9][1-9]))$

开机cpu风扇声音大_联想拯救者R720笔记本,开机显示暗屏,二修机多故障完美修复...

【机器型号】拯救者R720-15(7代I5)【主板版号】NM-B191【故障现象】笔记本不开机接同行送修笔记本拯救者R720-15,7代I5的机器,同行描述说不开机。【维修过程】 拿到机器按下开关没反映,三下五除二,扒下这台电脑的衣服,…

【转】刨根究底字符编码之六——简体汉字编码中区位码、国标码、机内码、外码、字形码的区别及关系

GB2312、GBK、GB18030等GB系列汉字编码方案的具体实现方式是怎样的?区位码是什么?国标码是什么?内码、外码、字形码又是什么意思?它们是如何转换的,又为什么要这样转换? 下面以GB2312为例来加以说明。 一、…

正则表达式:日期格式的校验(日期+时间)

日期格式如下:2020-09-25 00:00:00,并且中间-是可以省略的,那么我们到了后台就需要将时间给转换回来 ^((\d{2}(([02468][048])|([13579][26]))[\-]?((((0[13578])|(1[02]))[\-]?((0[1-9])|([1-2][0-9])|(3[01])))|(((0[469])|(11))[\-]?(…

公共链接url出错_SEO优化技巧:关于URL的优化方法

点击标题下「蓝色微信名」可快速关注URL优化需要遵循一些原则, 采用以下方法,网页的用户体验更佳,同时对搜索引擎更友好。01URL越短越好对于搜索引擎来说,只要URL不超过265Byte,收录就没有问题。如果使用几百个字母的U…

【转】刨根究底字符编码之七——ANSI编码与代码页

一、ANSI编码 1. 如前所述,在全世界所有国家和地区的文字符号统一编码的UCS/Unicode编码方案问世之前(UCS、Unicode后文有详细介绍),各个国家、地区为了用计算机记录并显示自己的字符,都在ASCII编码方案的基础上,设计了各自的编…

Angular 下拉搜索框实现

今天有个需求要写一个下拉搜索框&#xff0c;本来是下拉框的&#xff0c;由于内容太多&#xff0c;所以添加一个查找功能。根据博客进行改写的。参考了他的基本框架进行实现。 效果图&#xff1a; 输入框右边的白色箭头图片下载地址 <td>xxxxxxx</td> <td sty…

新手前端练手网站_编程到底难不难学?新手入门选择哪种语言好?

以下内容适合的读者&#xff1a;想要学习编程的小白一.编程到底难不难学&#xff1f;对于这个问题我的回答是不知道&#xff0c;学会了编程的人会说好学&#xff0c;中途就放弃的人会说很难&#xff0c;任何知识想要掌握好都不是一件容易的事情。所以我决定用自己的实际行动来证…

【转】刨根究底字符编码之八——Unicode编码方案概述

Unicode编码方案概述 1. 前面讲过&#xff0c;随着计算机发展到世界各地&#xff0c;于是各个国家和地区各自为政&#xff0c;搞出了很多既兼容ASCII但互相之间又不兼容的各种编码方案(微软统一称之为ANSI编码&#xff0c;具体体现为各种ANSI代码页)。 这样一来&#xff0c;同…

Angular 自定义属性指令-禁止input框输入空格-以及删除复制内容中的空格

创建一个ts文件&#xff0c;并在module.ts中定义 import { Directive, ElementRef, HostListener, Input } from angular/core; import { FormGroup, FormControl, NgControl } from angular/forms; Directive({selector: [input-noSpace]}) export class NoSpace {constructo…

基于androidx的快速开发框架_Vue企业级优雅实战07框架开发03封装基于MockJS的模拟数据...

预览本文的实现效果&#xff1a;# giteegit clone gitgitee.com:cloudyly/dscloudy-admin-single.git# githubgit clone gitgithub.com:cloudyly/dscloudy-admin-single.gitgit checkout 05_MockJS本文主要内容&#xff1a;基于 Mock JS&#xff0c;优雅设计网络请求的模拟数据…

【转】Net Framework,Net Core 和 Net Standard 区别

前几天我在一个群里看到有关这方面的讨论&#xff0c;最后感觉讨论的不是很清晰&#xff0c;有幸的是我们的项目去年就开始迁移NetCore的调研了&#xff0c;我个人多多少少也是有过这方面的研究。下面我将说一下我自己对着三个的认识如果有不足的地方&#xff0c;请大家指出。 …

记录一次SQL优化,增加索引,随便写的当笔记了

写了一个SQL&#xff0c;前端往返时间大约1.7秒&#xff0c;最终优化到一共150毫秒左右&#xff0c;应该还可以更好一些 下面说的有点乱&#xff0c;有空再好好总结一下吧。参考文章里面写的还是比较好的&#xff0c;只不过没有组合查询。 参考链接&#xff1a;https://zhuan…

使用函数求最大公约数 pta_高中数学选修教材2-导数第6课时《函数的单调性与导数》教学设计...

选修2-2第一章1.3.1 函数的单调性与导数一、先复习一下&#xff0c;上节课讲到了利用导数求曲线的切线方程(点我)&#xff0c;咱们这节课接着讲利用导数判断函数的单调性。二、做出图像形象生动&#xff0c;让学生看到当斜率为正(亦是导数为正)的时候函数图像是上升的&#xff…

Kafka幂等性与事务

kafka幂等性 博客https://www.cnblogs.com/smartloli/p/11922639.html 幂等性&#xff1a; 主要解决单会话&#xff08;producer宕机重启幂等性失效&#xff09; 主要是引入了ProducerID和SequenceNumber来实现幂等性 &#xff0c;当producer发送消息给broker后等待返回ack&…

【转】C#中枚举类型与静态变量

C#中enum类型&#xff0c;相较于其他基本数据类型来说比较特殊&#xff0c;他的本质上是一堆整数组成的结构体&#xff0c;并且支持与整型的显式转化。 既然是枚举类型&#xff0c;那么也就是说enum中的变量是不可以轻易改变的&#xff0c;所以C#将枚举类型认定成了static变量…

java程序员_Java程序员工资为什么这么高?

众多行业中&#xff0c;程序员当然属于高薪职业。无论是国内还是国外&#xff0c;IT行业的程序员、工程师&#xff0c;甚至连码农都要比其他行业的从业者的收入高很多&#xff01;尤其是作为IT界的“常青树”Java&#xff0c;原因是什么&#xff1f;01Java行业市场需求存在巨大…