Vim正则表达式示例

2018-04-27|Categories: Vim|Tags: |

匹配非ASCII字符

ASCII字符集在0x00 - 0x7F范围内定义字符。还有许多其他字符集(主要是欧洲字符集),它们在0x00 - 0x7F范围内定义与ASCII字符集相同的字符,还在0x80 - 0xFF范围内定义扩展字符集。因此,8位的单字节字符集 (Single-Byte-Character Sets, SBCS) 足以表示ASCII字符集以及许多欧洲语言的字符集。但是,一些非欧洲语言的字符集(如汉字)包含的字符数多于单字节编码方案可表示的字符数,因此需要多字节字符集 (MultiByte-Character Sets, MBCS) 编码。

如上图所示,缓冲区包含了ASCII字符、中文字符和中文标点,如果要匹配所有「非ASCII字符」,使用如下命令即可:

/[^\x00-\x7f]

匹配汉字

上图中,非ASCII字符只包括中文字符和中文标点,如果像下图这样一个文件包含了多种Unicode字符,同样的正则表达式匹配的就不只是中文字符了:

如果只想匹配中文,必须换一个正则表达式:

/[\u2e80-\u9fff]

这个正则表达式查找从Unicode代码点(Code Point)\u2e80\u9fff范围内的字符,也就是CJK字符。

在Unicode标准中,中日韩三国的文字统称为中日韩统一表意文字(CJK Unified Ideographs),在Unicode 6.3标准中占据的编码块有以下几个:

2E80..2EFF; CJK Radicals Supplement 中日韩部首增补
2F00..2FDF; Kangxi Radicals 康熙部首
3000..303F; CJK Symbols and Punctuation 中日韩符号和标点
31C0..31EF; CJK Strokes 中日韩笔画
3200..32FF; Enclosed CJK Letters and Months 带圈中日韩字母和月份
3300..33FF; CJK Compatibility 中日韩兼容
3400..4DBF; CJK Unified Ideographs Extension A 中日韩统一表意文字扩展A
4DC0..4DFF; Yijing Hexagram Symbols 易经六十四卦符号
4E00..9FFF; CJK Unified Ideographs 中日韩统一表意文字
F900..FAFF; CJK Compatibility Ideographs 中日韩兼容表意文字
FE30..FE4F; CJK Compatibility Forms 中日韩兼容形式
20000..2A6DF; CJK Unified Ideographs Extension B 中日韩统一表意文字扩展B
2A700..2B73F; CJK Unified Ideographs Extension C 中日韩统一表意文字扩展C
2B740..2B81F; CJK Unified Ideographs Extension D 中日韩统一表意文字扩展D
2F800..2FA1F; CJK Compatibility Ideographs Supplement 中日韩兼容表意文字增补

因为需要在一个较大范围内搜索匹配,所以Vim执行上述正则表达式会导致性能降低,出现明显的卡顿,最终匹配结果如下图:

注意红色方框内的中文感叹号、逗号、冒号没有被匹配,因为它们的代码点超出了前面的匹配范围:

匹配英文字符后面的中文冒号

/\a\zs\%uFF1A\ze\a
  • \a在Vim中表示大写字母和小写字母的集合
  • \zs不匹配字符,而是匹配字符的开始(Start)位置,等同于Perl中的顺序环视(?=)元字符
  • \%uFF1A就是中文冒号的Unicode代码点,也可以直接输入中文冒号
  • \ze类似\zs,不匹配字符,而是匹配字符的结束(End)位置,等同于Perl中的逆序环视(?<=)元字符

正则表达式组合起来的意思就是:匹配左边以字母开始、右边以字母结束的中文冒号。于是,下图红色方框中的「场景」后面的冒号就没有被匹配:

Leave A Comment