类名写法
POSIX 风格用成对的方括号加冒号包裹类名,再嵌在外层字符类里表示「属于该类别的一个字符」。写法上是双层括号:外层括号界定字符类,内层括号里是类别名称,这也是它看起来别扭的原因。
与本地化设置相关
字母、数字、大小写这些类别的实际范围由本地化设置决定。在最小本地化设置下它们通常只认半角英文与数字;切换到多语言本地化后范围可能扩大。因此同一条命令在不同服务器上跑出不同结果并不罕见。
基本信息
| 写法形式 | 外层方括号内写冒号包裹的类名 |
|---|---|
| 常见类名 | 字母、数字、字母数字、空白、大写、小写、标点、十六进制数字、可打印字符 |
| 与简写类关系 | 用途相近但定义来自 POSIX 标准与本地化设置,不是引擎默认的字符语义 |
| 本地化影响 | 多语言本地化下字母类可能包含非 ASCII 字符 |
| 支持情况 | grep、sed、awk 等命令行工具与主流正则引擎普遍支持 |
| 常见误写 | 只写一层方括号会让工具把整串当成普通字符集合 |
典型使用场景
- 命令行文本处理里做字符类别判断,语义比手写区间更清楚
- 校验只含字母数字的字段,避免手写区间遗漏字符
- 清洗数据时保留可打印字符、剔除控制字符
- 统计空白、标点等类别的数量
- 在脚本里跨发行版复用过滤规则,同时固定本地化设置以保证结果一致
POSIX 类的常见用法
POSIX 类的常见用法
grep -E '^[[:alpha:]]+$' f.txt # 整行仅由字母组成
grep -E '[[:digit:]]{4}' f.txt # 连续四位数字
grep -E '^[[:alnum:]_]+$' f.txt # 字母数字下划线
grep -v '[[:print:]]' f.txt # 筛出含不可打印字符的行
sed 's/[[:space:]]\+/ /g' f.txt # 压缩连续空白
tr -d '[:cntrl:]' < f.txt | head # 删除控制字符
LC_ALL=C grep -E '^[[:alpha:]]+$' f.txt # 固定本地化设置,结果可复现常用类名含义
| 类名 | 含义 | 常见用途 |
|---|---|---|
| 字母类 | 字母字符 | 姓名与单词匹配 |
| 数字类 | 十进制数字 | 数值字段匹配 |
| 字母数字类 | 字母与数字 | 标识符校验 |
| 空白类 | 空白字符 | 切分与压缩 |
| 标点类 | 标点符号 | 剥离标点 |
| 十六进制类 | 十六进制数字 | 编号与哈希匹配 |
| 可打印类 | 可打印字符 | 脏数据筛查 |
范围写法与类名写法在非默认本地化下可能表现不同:范围依赖编码顺序,类名依赖类别定义。要求结果可复现时,显式设置最小本地化设置是最省事的做法。
类名写错时工具不会报错,而是把整串字符当成集合处理,于是模式静默变成「匹配其中任意一个字符」。模式结果异常且看起来毫无关联时,先把类名拼写核对一遍。