使用SED做正则替换时报错\1 not defined in the RE,该如何处理?
错误原因
- sed 默认使用*基础正则表达式(BRE)*语法,该语法下捕获组必须用
\(和\)包裹,你写的普通括号()会被识别为普通字符,没有实际生成捕获变量,因此调用\1时会提示未定义。 - BRE 语法下量词
+需要转义为\+才能生效,未转义的+只会被当作普通加号字符匹配。 - 额外说明:原正则里的
@无特殊含义,不需要加转义符\。
解决方案
提供两种可直接使用的方案:
方案1:兼容默认BRE模式(无额外参数,跨环境兼容性最高)
调整转义规则后的命令如下:
sed 's|@done.\([0-9]\+\).\([0-9]\+\).\([0-9]\+\)|#done/\1/\2/\3|'
如果需要严格匹配@done(2021-08-13的固定格式,避免误匹配其他相近字符串,可以使用更精准的写法:
sed 's|@done(\([0-9]\{4\}\)-\([0-9]\{2\}\)-\([0-9]\{2\}\)|#done/\1/\2/\3|'
方案2:开启扩展正则模式(语法更简洁)
给sed加扩展正则参数,就不需要额外转义括号和量词:
- GNU/Linux 环境(常见的CentOS、Ubuntu等系统)使用
-r参数:
sed -r 's|@done.([0-9]+).([0-9]+).([0-9]+)|#done/\1/\2/\3|'
- macOS 环境使用
-E参数:
sed -E 's|@done.([0-9]+).([0-9]+).([0-9]+)|#done/\1/\2/\3|'
内容的提问来源于stack exchange,提问作者Gary Learned
相关产品推荐
相关产品推荐

