你有一个问题,决定使用正则解决,现在你有两个问题了?!

2022-08-29 10:13:00 +08:00
 jurassic2long

工作多年,每次使用正则表达式都要测试好几次才敢用。 大家来分享一下自己使用正则的技巧, 或者分享遇到的大坑,让大家乐呵乐呵~

5265 次点击
所在节点    程序员
37 条回复
fstar
2022-08-29 17:52:05 +08:00
正则简单的还好,复杂的头晕,可能还有潜藏的 case 没有覆盖以及性能问题

个人认为能不用就不用。

骚操作:读到 `<div class="member">用户名</div>`,用 string.repace(/^<div class="member">(.*)</div>$/, $0) 提取用户名。
libook
2022-08-29 17:59:45 +08:00
测试覆盖好边界,注释写清楚。
yjhatfdu2
2022-08-29 18:34:00 +08:00
更复杂的场景写 parser
Terry05
2022-08-29 19:04:36 +08:00
正则这东西真特么神奇,隔一段时间绝对可以忘得一干二净!
zlowly
2022-08-29 20:32:07 +08:00
正则这东西,真是只有在所有可以使用的正则的地方经常使用,才能体现投入产出比。
但是麻烦的就是在 php,python,grep,vim,sed 各类可以使用的地方,他们的正则在细微处总有差异,特别在转义方面有着各自的坚持,实在是令人抓狂。
zlowly
2022-08-29 20:35:43 +08:00
除了上面提到的 regex101.com ,补充个 debuggex.com 的图形化显示也能较好辅助理解。
wxf666
2022-08-29 23:22:34 +08:00
@bulay 你这是遇到“灾难性回溯”(或“回溯陷阱”)了

随便一搜,资料很多。比如: https://zh.javascript.info/regexp-catastrophic-backtracking
liuxu
2022-08-30 00:29:25 +08:00
@fstar #21 linux 管道流式分析日志都是用这种方式提取,包括一些日志软件
ragnaroks
2022-08-30 08:15:49 +08:00
这个笑话我在学校学 C 的时候老师就讲过了,大意是正则晦涩难懂,其实无他手熟尔
jackmod
2022-08-30 08:42:54 +08:00
regex 是天书,非常需要注释。所以每写一条都要在旁边写一些例子,便于后期阅读。
answerhuang
2022-08-30 09:14:36 +08:00
@HankAviator 自己写出同样功能的代码, 效率不一定比正则好. 所以放心用吧.
jinliming2
2022-08-30 09:34:22 +08:00
感觉还是因为害怕使用,所以不愿意用,尽可能避免用。
但是经常用的话,看正则跟看普通代码一样没啥区别,逻辑不复杂的正则根本不需要注释。除非括号嵌套比较深的,如果正则引擎或语言其他特性支持的话,给换行带个缩进就好。

我有这样的想法是在之前学 iptables 的时候,一堆参数记不住,都是一个字母的,也没啥具体含义的参数,所以我就不想用。可是 iptables 用的人很多啊,经常用的人这些参数都能直接写出来的,没啥难度哇。
正则也是,如果自己不会的话,是不愿意用,但自己会用的话,效率还是很高的。
jinliming2
2022-08-30 09:42:25 +08:00
@jinliming2 emmmm ,iptables 参数没啥具体意义,这个说法不太对。是说参数含义比较难记。
bulay
2022-08-30 09:51:21 +08:00
@wxf666 具体内容忘了,应该是这个原因.看完之后豁然开朗.其实就是两个贪婪标志加边界问题.被匹配对象太长没有注意到
AS4694lAS4808
2022-08-30 10:23:14 +08:00
以前做过一些硬件报文的解析,几千个字符,每个数据之间用空格隔开,提取数据的时候还是正则香。。。
11232as
2022-08-30 16:12:47 +08:00
regex coach ,很棒的正则验证软件,可惜只有 Windows 端得
dousha99
2022-08-31 10:28:12 +08:00
感觉标题的这个现象是因为对正则表达式过度神化了。如果你无法用正则语言描述你的数据(或你需要处理的子集),那么你的数据八成是没法通过正则表达式处理的,还是老老实实写字符串处理代码比较好。

比如「匹配 n 个 a 之后跟着 n 个 b 的字符串」,这个需求是根本不能用正则表达式做的。同理「匹配身份证是否有效」这个需求也是(除了枚举所有有效的身份证号)无法完整地用正则表达式实现的(只是匹配 18 位数字或者 17 位数字带一个 X 是不完整的)。1@1 是合法的邮箱么? 13600000000 是合法的手机号么?很多我们觉得「或许可以用正则处理」的问题实际上是在操作不正则的数据(比如测试邮箱是否合法),或者操作虽然因是有限语言而正则但是枚举所有句子根本不可行的数据(比如测试身份证号是否合法)。

当然,算上 Perl 给大家带来的那种 irregular 的正则,或许可以处理一点点上下文无关的数据。但还是,很怪。

这是一个专为移动设备优化的页面(即为了让你能够在 Google 搜索结果里秒开这个页面),如果你希望参与 V2EX 社区的讨论,你可以继续到 V2EX 上打开本讨论主题的完整版本。

https://www.v2ex.com/t/876101

V2EX 是创意工作者们的社区,是一个分享自己正在做的有趣事物、交流想法,可以遇见新朋友甚至新机会的地方。

V2EX is a community of developers, designers and creative people.

© 2021 V2EX