在zsh正则表达式中匹配Unicode字符

4

我想确保一个变量不包含特定的字符(在这种情况下是'α'),但以下代码失败了(返回1):

FOO="test" && [[ $FOO =~ '^[^α]*$' ]]

编辑:根据下方stema的反馈更改了模式,只要求从开头到结尾匹配“非'α'”字符。

将'α'替换为例如'x'可以正常工作。为什么使用'α'时会失败,如何使其正常工作?

系统信息:

$ zsh --version
zsh 4.3.11 (i386-apple-darwin11.0)
$ locale
LANG="en_GB.UTF-8"
LC_COLLATE="en_GB.UTF-8"
LC_CTYPE="en_GB.UTF-8"
LC_MESSAGES="en_GB.UTF-8"
LC_MONETARY="en_GB.UTF-8"
LC_NUMERIC="en_GB.UTF-8"
LC_TIME="en_GB.UTF-8"
LC_ALL="en_GB.UTF-8"

编辑2:我现在在一台运行Ubuntu 11.10的Linux机器上进行了测试,使用相同的区域设置运行zsh 4.3.11,并且它可以正常工作 - 即FOO="test" && [[ $FOO =~ '^[^α]*$' ]]返回成功。 我正在运行Mac OS X 10.7.2。

3个回答

1
用这个正则表达式.*[^α].*,你无法测试字符串中是否存在α。它所测试的是:字符串中是否有一个字符不是α
如果你想要检查字符串中没有这个字符,可以这样做:
FOO="test" && [[ $FOO =~ '^[^α]*$' ]]

这将检查从开头到结尾的完整字符串是否由非“α”字符组成。


哦,对了。所以它不一定需要匹配整个字符串。是的,那么你是正确的,应该是FOO="test" && [[ $FOO =~ '^[^α]*$' ]]。但那仍然失败了。将'α'更改为'x'就成功了,因此在这里使用'α'字符时必须有些东西不能正常工作。 - beta

0

最简单的方法是在开头使用负向预查来表达:

^(?!.*α)

这句话的意思是“从起点向前看,我不应该能够在任何地方看到α。”

使用前瞻的优点是它们是非捕获的,因此您可以将它们与其他捕获正则表达式结合使用,例如在输入中查找不包含α的引号中数字组的情况,使用以下内容:^(?!.*α)"(\d+)"


0
由于某些原因,我的构建系统出现了类似的问题,而我的笔记本电脑上安装了ZSH 5.0.2版本(其中Unicode按预期工作),而我的构建系统上安装了ZSH 4.3.17版本。我觉得ZSH 5在正则表达式模式中没有Unicode字符的问题。
具体来说,解析键/值对:
[[ "revision/author=Ľudovít Lučenič" =~ '^([^=]+)=(.*)$' ]]
echo "$match[1]:$match[2]"

渲染

:                               # ZSH 4.3.17
revision/author:Ľudovít Lučenič # ZSH 5.0.2

此外,我认为ZSH 4在Unicode支持方面存在一些缺陷。

更新:经过一番调查,我发现正则表达式中的点号无法匹配ZSH 4中的字母'č'。一旦我将模式更新为:

[[ "revision/author=Ľudovít Lučenič" =~ '^([^=]+)=((.|č)*)$' ]]
echo "$match[1]:$match[2]"

我在两个ZSH版本中得到了相同的结果。虽然我不知道为什么这个字母会成为问题,但这可能有助于某些人解决这个缺陷。


网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接