Mac OS X下fgrep通过-f文件精准匹配时子串项匹配失效问题
Mac OS X 10.15.1 下 fgrep 整行匹配异常的解决方法
在Mac OS X 10.15.1默认的BSD版本fgrep中,使用-x或-w结合-f qlist参数匹配整行内容时,若qlist中存在短前缀模式(如CMGC_CDK1是CMGC_CDK10的前缀),会出现长模式(CMGC_CDK10)无法匹配的情况,而Ubuntu上的GNU grep无此问题。
问题原因
这是BSD grep的特性:当使用-F(fgrep等价于grep -F)结合-f加载模式文件时,会自动对模式进行字典序排序,导致短前缀模式优先被匹配,进而干扰了长模式的匹配逻辑(即使使用-x整行匹配,也会因内部排序后的匹配顺序出现异常)。
解决方法
调整模式顺序
将qlist中的模式按字符串长度从长到短排序,确保长模式先被处理:sort -r qlist > sorted_qlist fgrep -x -f sorted_qlist biglist执行后即可正确匹配到
CMGC_CDK10等长模式行。替换为GNU grep
通过Homebrew安装GNU版本的grep(默认命名为ggrep):brew install grep使用
ggrep执行命令,GNU grep不会自动排序模式文件内容,完全按原顺序匹配:ggrep -F -x -f qlist biglist用awk实现跨平台匹配
awk的逻辑不受系统grep版本差异影响,直接实现精准整行匹配:awk 'NR==FNR {targets[$0]; next} $0 in targets' qlist biglist该命令先将qlist的所有行存入数组,再遍历biglist输出存在于数组中的行,完美符合预期需求。
内容的提问来源于stack exchange,提问作者Roland Dunbrack
相关产品推荐
相关产品推荐

