sed提取带值#define名称的正则模式故障排查
问题排查与解决方案
原正则的核心错误
你的sed模式pattern="#define (${toRemove})([a-zA-Z0-9_]+)[^\(\)]+\s.*"存在两个致命问题:
- 错误排除带括号的值:
[^\(\)]+要求匹配的内容完全不包含(和),但目标行里的((cpu_subtype_t) 0)这类带类型转换的值本身就有括号,直接被这个规则过滤掉了。 - 逻辑方向颠倒:你需要排除的是**宏名后紧跟
(**的函数式宏,而不是排除所有带括号的内容,原正则的匹配逻辑完全不符合需求。
正确的sed实现方案
1. 提取所有非函数式#define行(排除带参数的宏)
如果只是要保留所有带值的#define,排除带参数的,用以下命令:
sed -n '/^#define [a-zA-Z0-9_]*([^)]*)/!p' input_header.h
- 逻辑:
/^#define ...(/匹配带参数的函数式宏行,!p表示不打印这些行,只打印剩下的带值#define行。
2. 匹配特定前缀的宏(比如${toRemove}开头的)
如果只需要提取${toRemove}前缀的带值宏,调整为:
toRemove="CPU_SUBTYPE_" sed -n "/^#define ${toRemove}[a-zA-Z0-9_]*(/!p" input_header.h
3. 仅提取宏名和对应值(去掉#define前缀)
如果要进一步提取宏名与值的部分,去掉#define前缀:
toRemove="CPU_SUBTYPE_" sed -n "/^#define ${toRemove}[a-zA-Z0-9_]*(/!s/^#define \(.*\)/\1/p" input_header.h
示例验证
针对你的测试用例:
- 保留行:
#define CPU_SUBTYPE_MASK 0xff000000、#define CPU_SUBTYPE_VAX_ALL ((cpu_subtype_t) 0) - 排除行:
#define CPU_SUBTYPE_INTEL(f, m)...
用上述命令可以精准过滤,不会遗漏带括号值的目标行。
内容的提问来源于stack exchange,提问作者Arsynth
相关产品推荐
相关产品推荐

