如何在 perl 正则表达式替换命令中使用 unicode 字符?

gee*_*ley 2 regex unicode perl command-line utf-8

当使用 unicode 字符时这不起作用(在 Ubuntu bash 中):

\n
$ perl -pC -e\'s/[\xc3\xa0]/a/gu\' <<< \'\xc3\xa0\'\n\xc3\xa0\n$ perl -pC -e\'s/[b]/a/gu\' <<< \'b\'\na\n
Run Code Online (Sandbox Code Playgroud)\n

尽管它似乎受 PCRE 支持(至少根据regex101)。

\n

我究竟做错了什么?我在 perl 命令中缺少一些标志吗?

\n

这在 javascript 中“正常工作”,所以如果我能在命令行中为此提供一个简单的单行代码,我将使用节点......但我仍然想知道为什么 perl 命令不起作用。

\n
\n

对于上下文:

\n

我正在尝试使用类似的替换/[\xc3\xa0\xc3\xa2\xc3\xa1\xc3\xa3\xc3\xa4]/a/g/[\xc3\xb2\xc3\xb4\xc3\xb3\xc3\xb5\xc3\xb6]/o/g等替换来 asciify 字典文件(即删除单词列表的重音等),因此我可以使用它来使拼写检查重音不敏感(例如在 IntelliJ Idea 中)。

\n

基本上,这些是制作“asciified”额外字典的步骤:

\n
    \n
  1. 下载该语言的 .dic 文件(所有单词的列表)
  2. \n
  3. 使用grep过滤包含非ascii/可替换字符的单词
  4. \n
  5. 连续使用正则表达式替换使单词不区分重音
  6. \n
  7. 在IDE中导入asciified .dic文件(除了标准语言词典)
  8. \n
\n

zdi*_*dim 8

解决所有这些问题的一种实用方法是使用Text::Unidecode

\n
perl -C -MText::Unidecode -pe\'unidecode($_)\'  <<< \'\xc3\xa0\'\n
Run Code Online (Sandbox Code Playgroud)\n

印刷a。该模块将 Unicode 文本音译为纯 ASCII。

\n

另一种方法:使用Unicode::Normalize分解字符(“标准化”),以便字符及其变音符号(组合重音符号)被分成自己的代码点,同时它们仍然形成有效的字素,然后删除变音符号(\\p{NonspacingMark}\\p{Mn})用一个简单的正则表达式。

\n

这两种方式都会有例外和边缘情况,但我认为它可能只是满足您的需要。

\n
\n

对于包含特定(文字)字符的代码,需要通过带有或带有命令行标志的utf8 pragma告诉 Perl 程序源代码是 UTF-8use utf8;-Mutf8

\n
perl -C -Mutf8 -pe\'s/[\xc3\xa0]/a/g\' <<< \'\xc3\xa0\'\n
Run Code Online (Sandbox Code Playgroud)\n