F.P*_*F.P 120 regex complexity-theory dictionary
这可能听起来像一个愚蠢的问题,但我与我的一些开发人员进行了长时间的谈话,这听起来像是一件有趣的事情.
所以; 你的想法是什么 - 正则表达式是什么样的,永远不会被任何字符串匹配!
编辑:我为什么要这个?好吧,首先是因为我发现想到这样一个表达式很有趣,其次因为我需要它来制作一个脚本.
在该脚本中,我将字典定义为Dictionary<string, Regex>.如您所见,它包含一个字符串和一个表达式.
基于该字典,我创建的方法都使用这个字典作为他们应该如何完成工作的参考,其中一个匹配正则表达式与解析的日志文件.
如果表达式匹配,Dictionary<string, long>则为另一个表达式添加表达式返回的值.因此,为了捕获与字典中的表达式不匹配的任何日志消息,我创建了一个名为"unknown"的新组.
对于这个组,添加了与其他任何东西不匹配的所有内容.但是为了防止"未知"表达式(偶然)不匹配日志消息,我不得不创建一个绝对不会匹配的表达式,无论我给它什么字符串.
因此,你有理由这个"不是一个真正的问题"......
Ale*_*lli 74
杠杆negative lookahead:
>>> import re
>>> x=r'(?!x)x'
>>> r=re.compile(x)
>>> r.match('')
>>> r.match('x')
>>> r.match('y')
这个RE在术语上是矛盾的,因此永远不会匹配任何东西.
注意:
 
在Python中,re.match()隐式地将一个字符串开头的anchor(\A)添加到正则表达式的开头.此锚点对性能很重要:没有它,将扫描整个字符串.那些不使用Python的人会想要明确地添加锚点:
\A(?!x)x
Fer*_*yer 62
这实际上非常简单,虽然它取决于implementation/flags*:
$a
将a在字符串结尾后匹配一个字符.祝好运.
警告:
 
此表达式很昂贵 - 它将扫描整行,找到行尾锚点,然后才找到a并返回负匹配.(有关详细信息,请参阅下面的评论.)
*最初我没有考虑多线模式正则表达式,其中$也匹配线的末尾.事实上,它会在换行符之前匹配空字符串,所以像往常一样的普通字符a永远不会出现$.
Mar*_*ers 35
错过了一个:
^\b$
它无法匹配,因为空字符串不包含单词边界.在Python 2.5中测试.
Ama*_*osh 34
环视四周:
(?=a)b
对于正则表达式新手:正向前看(?=a)确保下一个字符是a,但不会更改搜索位置(或在匹配的字符串中包含"a").现在确认了下一个字符a,regex(b)的剩余部分仅在下一个字符匹配时才匹配b.因此,此正则表达式匹配只有一个字符既a与b在同一时间.
Kni*_*nio 20
$.
.^
$.^
(?!)
Bra*_*ert 11
a++a
至少有一个a跟随任意数量a的,没有回溯.然后尝试再匹配一个a.
这相当于放入a+一个独立的子表达式,然后是另一个子表达式a.
(?>a+)a
\B\b
\b匹配单词边界 - 字母与非字母(或字符串边界)之间的位置.
\B是它的补充 - 它匹配两个字母之间或非字母之间的位置.
他们在一起无法匹配任何位置.
也可以看看:
$^或者怎么样(?!)? 
这似乎有效:
$.
最快的将是:
r = re.compile(r'a^')
r.match('whatever')
“ a”可以是任何非特殊字符(“ x”,“ y”)。Knio的实现可能会更纯净,但是对于所有不以您选择的任何字符开头而不是'a'开头的字符串来说,这种方法都会更快,因为在这种情况下,它将不匹配第一个字符,而不是第二个字符。
这不适用于 Python 和许多其他语言,但在 Javascript 正则表达式中,[]是无法匹配的有效字符类。因此,无论输入什么,以下内容都应该立即失败:
var noMatch = /^[]/;
我更喜欢它,/$a/因为对我来说,它清楚地传达了它的意图。至于何时需要它,我需要它,因为我需要基于用户输入的动态编译模式的后备。当模式无效时,我需要将其替换为不匹配的模式。简化后,它看起来像这样:
try {
    var matchPattern = new RegExp(someUserInput);
}
catch (e) {
    matchPattern = noMatch;
}
这么多好的答案!
与 @nivk 的答案类似,我想分享 Perl 对于不同变体的不匹配正则表达式的性能比较。
正则表达式速度:
Total for   \A(?!x)x: 69.675450 s, 1435225 lines/s
Total for       a\bc: 71.164469 s, 1405195 lines/s
Total for    (?>a+)a: 71.218324 s, 1404133 lines/s
Total for       a++a: 71.331362 s, 1401907 lines/s
Total for         $a: 72.567302 s, 1378031 lines/s
Total for     (?=a)b: 72.842308 s, 1372828 lines/s
Total for     (?!x)x: 72.948911 s, 1370822 lines/s
Total for       ^\b$: 79.417197 s, 1259173 lines/s
Total for         $.: 88.727839 s, 1127041 lines/s
Total for       (?!): 111.272815 s, 898692 lines/s
Total for         .^: 115.298849 s, 867311 lines/s
Total for    (*FAIL): 350.409864 s, 285380 lines/s
正则表达式速度:
Total for   \A(?!x)x: 128.336729 s, 1564805 lines/s
Total for     (?!x)x: 132.138544 s, 1519783 lines/s
Total for       a++a: 133.144501 s, 1508301 lines/s
Total for    (?>a+)a: 133.394062 s, 1505479 lines/s
Total for       a\bc: 134.643127 s, 1491513 lines/s
Total for     (?=a)b: 137.877110 s, 1456528 lines/s
Total for         $a: 152.215523 s, 1319326 lines/s
Total for       ^\b$: 153.727954 s, 1306346 lines/s
Total for         $.: 170.780654 s, 1175906 lines/s
Total for       (?!): 209.800379 s, 957205 lines/s
Total for         .^: 217.943800 s, 921439 lines/s
Total for    (*FAIL): 661.598302 s, 303540 lines/s
(Intel i5-3320M 上的 Ubuntu、Linux 内核 4.13、Perl 5.26)
永远不匹配任何内容的最佳正则表达式是空正则表达式。但我不确定所有正则表达式引擎都会接受这一点。
另一个解决方案是创建一个不可能的正则表达式。我发现无论$-^文本大小如何,只需要两个步骤即可计算(https://regex101.com/r/yjcs1Z/1)。
$^并$.需要 36 个步骤来计算 -> O(1)\b\B在我的样本上需要 1507 步,并且随着字符串中字符数的增加而增加 -> O(n)| 归档时间: | 
 | 
| 查看次数: | 15362 次 | 
| 最近记录: |