玩转一下正则表达式

发布于 2022-09-27 12:29:45 字数 8150 浏览 114 评论 0

看了一篇用正则把自己玩死的博客,代码是这个样子的,结果是把 cpu 跑死,或者跑不出来结果。

public static void main(String[] args) {
    String badRegex = "^([hH][tT]{2}[pP]://|[hH][tT]{2}[pP][sS]://)(([A-Za-z0-9-~]+).)+([A-Za-z0-9-~\\\\/])+$";
    String bugUrl = "http://www.fapiao.com/dddp-web/pdf/download?request=6e7JGxxxxx4ILd-kExxxxxxxqJ4-CHLmqVnenXC692m74H38sdfdsazxcUmfcOH2fAfY1Vw__%5EDadIfJgiEf";
    if (bugUrl.matches(badRegex)) {
        System.out.println("match!!");
    } else {
        System.out.println("no match!!");
    }
}

正则:^([hH][tT]{2}[pP]://|[hH][tT]{2}[pP][sS]://)(([A-Za-z0-9-~]+).)+([A-Za-z0-9-~\\/])+$
字串:http://www.fapiao.com/dddp-web/pdf/download?request=6e7JGxxxxx4ILd-kExxxxxxxqJ4-CHLmqVnenXC692m74H38sdfdsazxcUmfcOH2fAfY1Vw__%5EDadIfJgiEf

拷贝到 Online regex tester and debugger: PHP, PCRE, Python, Golang and JavaScript 的 regex101 试一下,也能看到报告了灾难性回溯 Catastrophic backtracking 错误。

点击左边的 Debugger,会有 动画显示匹配过程,是一个很好地可视化过程。

最简单的修复,是调整一下 正则,让匹配能成功进行,但是这个只是治标,还得考虑治本:

  1. 识别清晰正则表达式的场景(本例就不是正则表达式的正确使用场景,而应该使用类似于URLParser的解析器。
  2. Java 正则匹配,可以作出某种限定,避免灾难性回溯。

想起若干年前,做靓号规则的时候,电信的 BOSS 系统也是用正则表达式来匹配一个手机号码,是否符合 AABB,或者 AAAA 等模式的,正则表达式写起来也是相当不好看,真是王婆婆的裹脚又臭又长,所以轮到我来玩了,我就直接实现了 ABC 表达式,直接配置 AABB 或者 AAAA 等形式的表达式,就可以匹配是否是某种级别的靓号了,不亦乐乎。

Removing the MySQL root password 上看到一个正则 temporary password(.*): \K(\S+),不理解其中的 \K 的含义,查询文档,了解了是重置前面所有的捕获,还有这种骚骚的用法

\K can be used to reset the match start since PHP 5.2.4. For example, the pattern foo\Kbar matches "foobar", but reports that it has matched "bar". The use of \K does not interfere with the setting of captured substrings. For example, when the pattern (foo)\Kbar matches "foobar", the first substring is still set to "foo".

参考

  1. Escape sequences
  2. mysql_temporary_password regex test

------------------------------------

grep 提取多个值 ggrep -oP "appId.:.\K([\w_]+)|deviceId.:.\K([\w_]+)" 1.log paste -d ' ' - - regex101

$ grep -oP "appId.:.\K([\w_]+)|deviceId.:.\K([\w_]+)"  1.log  | paste -d ' ' - -
APP_79D5EC7B7C55465F8FB8114C87517CF6 DEV_C77897738BF243B1AA1E8E316850F410
APP_79D5EC7B7C55465F8FB8114C87517CF6 DEV_C77897738BF243B1AA1E8E316850F410
APP_79D5EC7B7C55465F8FB8114C87517CF6 DEV_C77897738BF243B1AA1E8E316850F410
DEV_37A4DD248CDC4DB7ADE0D3626CAB24CA APP_1698D243C3D04C46B1D488EBAE2F8348

jq 提取 grep -oP "\[\K({.*})(?=\])" 1.log | jq -c '. | {appId: .appId, deviceId: .deviceId}' regex101

$ grep -oP "(?<=\[)({.*})(?=\])" 1.log | jq -c '. | {appId: .appId, deviceId: .deviceId}'
{"appId":"APP_79D5EC7B7C55465F8FB8114C87517CF6","deviceId":"DEV_C77897738BF243B1AA1E8E316850F410"}
{"appId":"APP_79D5EC7B7C55465F8FB8114C87517CF6","deviceId":"DEV_C77897738BF243B1AA1E8E316850F410"}
{"appId":"APP_79D5EC7B7C55465F8FB8114C87517CF6","deviceId":"DEV_C77897738BF243B1AA1E8E316850F410"}
{"appId":"APP_1698D243C3D04C46B1D488EBAE2F8348","deviceId":"DEV_37A4DD248CDC4DB7ADE0D3626CAB24CA"}
  1. demo 1.log
  2. How to use grep to extract multiple groups
  3. brew install grep How to install and use GNU Grep in OSX

---------------------------------------------------------

正则表达式详细介绍 里面看到在线工具 regexr.com 也不错,可以作为一个备份工具

--------------------------------------

普通人的正则表示式教程 一本免费的英文教程,向初学者介绍正则表达式,实例较多。

每一个正则,都有在线的解析高烈显示以及结构化图,例如:

UUID

[\da-f]{8}-([\da-f]{4}-){3}[\da-f]{12}/i RegExr Visual

一些资源

  1. awesome-regex A curated collection of awesome Regex libraries, tools, frameworks and software
  2. regex tag on StackOverflow
  3. StackOverflow RegEx FAQ
  4. r/regex
  5. RexEgg
  6. Regular-Expressions.info
  7. Regex Crossword
  8. Regex Golf

-------------------------------------------------

Regular Expression Tester and Visualizer

如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。

扫码二维码加入Web技术交流群

发布评论

需要 登录 才能够评论, 你可以免费 注册 一个本站的账号。
列表为空,暂无数据

关于作者

时光无声

暂无简介

0 文章
0 评论
23 人气
更多

推荐作者

謌踐踏愛綪

文章 0 评论 0

开始看清了

文章 0 评论 0

高速公鹿

文章 0 评论 0

alipaysp_PLnULTzf66

文章 0 评论 0

热情消退

文章 0 评论 0

白色月光

文章 0 评论 0

    我们使用 Cookies 和其他技术来定制您的体验包括您的登录状态等。通过阅读我们的 隐私政策 了解更多相关信息。 单击 接受 或继续使用网站,即表示您同意使用 Cookies 和您的相关数据。
    原文