Python正则表达式搜索转义错误:升级Win10与Django2.10后报错
解决正则表达式中的"bad escape \N"错误
这个问题和编码参数完全无关,核心是新版本Python的re模块对正则转义序列的校验变严格了,咱们一步步理清楚:
为什么之前正常现在报错?
在旧版本的Python或re模块中,对非法转义序列(比如\N后面没有跟合法的Unicode字符名)的处理比较宽松,会直接把\N当作字面的N来匹配。但升级后,对应Python版本(Django 2.10适配Python 3.7+)的re模块严格遵循了正则规范:\N是专门用来匹配Unicode字符名的特殊转义(比如\N{GREEK LETTER ALPHA}匹配希腊字母α),而你的表达式里\N后面直接跟了I,属于无效转义,所以触发了错误。
针对性解决方案
要根据你的实际匹配需求调整代码:
情况1:你要匹配的是\x03(字节0x03)后紧跟N、I、B、A四个字节
那之前的\N是多余的反斜杠,直接去掉就行:
foo = abin.read() bar = re.search(b'\x03NIBA', foo)
情况2:你确实要匹配\x03后紧跟字面的\N(即字节0x5C + 0x4E)
这时候需要正确转义反斜杠,有两种简洁写法:
- 使用双重转义(字节串中
\\表示字面\,正则里再转义一次,所以总共四个反斜杠):
bar = re.search(b'\x03\\\\NIBA', foo)
- 更推荐用原始字节串,原始字符串会忽略所有转义,直接把内容当作字面量:
bar = re.search(br'\x03\NIBA', foo)
为什么你之前尝试双重转义无效?
大概率是转义层数没搞对——如果用非原始字节串,要匹配一个字面的\,需要在字节串里写\\(表示一个\),同时正则表达式里又要把\当作字面量,所以得再转义一次,也就是总共\\\\才能对应一个字面\。用原始字节串就不会有这种嵌套转义的麻烦,建议优先选这种方式。
内容的提问来源于stack exchange,提问作者Xeberdee




