假设有 2 个主机具有不同的命名约定......
ab_01
和ab_cd
我想确保他们的命名约定符合一定的标准。
因此,我编写了简单的脚本来测试它。
wolf@linux:~$ host='ab_01'
wolf@linux:~$ if [[ $host =~ [a-z][a-z]_[a-z][a-z] ]]; then echo True; else echo False; fi
False
wolf@linux:~$ if [[ $host =~ [a-z][a-z]_[0-9][0-9] ]]; then echo True; else echo False; fi
True
有用!
下一步是在 Shell 中将这 2 个正则表达式与 OR 运算符组合起来,即||
if [[ $host =~ [a-z][a-z]_[a-z][a-z] || $host =~ [a-z][a-z]_[0-9][0-9] ]];
then
echo True
else
echo False
fi
我们来测试一下
wolf@linux:~$ echo $host
ab_01
wolf@linux:~$ if [[ $host =~ [a-z][a-z]_[a-z][a-z] || $host =~ [a-z][a-z]_[0-9][0-9] ]];
> then
> echo True
> else
> echo False
> fi
True
wolf@linux:~$
它适用于ab_01
和ab_cd
。
然而,当我向主机名添加更多字符时,当它应该是 False 时,我仍然得到 True。
让我们用host='ab_0123'
and来测试一下host='ab_cdef'
wolf@linux:~$ host='ab_0123'
wolf@linux:~$ if [[ $host =~ [a-z][a-z]_[a-z][a-z] || $host =~ [a-z][a-z]_[0-9][0-9] ]];
> then
> echo True
> else
> echo False
> fi
True
wolf@linux:~$
另一个测试也显示 True 而不是 False
wolf@linux:~$ host='ab_cdef'
wolf@linux:~$ if [[ $host =~ [a-z][a-z]_[a-z][a-z] || $host =~ [a-z][a-z]_[0-9][0-9] ]];
> then
> echo True
> else
> echo False
> fi
True
wolf@linux:~$
这段代码有什么问题以及如何修复它?
答案1
与模式匹配不同,正则表达式匹配不锚定到字符串的开头/结尾,因此匹配任何地方在字符串中就足够了。 (它更像是“搜索”而不是“匹配”,我认为某些 Python 函数名称可以区分。)ab_cdef
contains ab_cd
,匹配。
^
您必须使用and显式锚定模式$
:
$ if [[ foobar =~ o ]]; then echo yes; else echo no; fi
yes
$ if [[ foobar =~ ^o$ ]]; then echo yes; else echo no; fi
no
您也可以||
将替换放在正则表达式中:
re='^[a-z][a-z]_([0-9][0-9]|[a-z][a-z])$'
if [[ $host =~ $re ]]; then ...
(或者对于更宽松的正则表达式允许ab_a0
:^[a-z][a-z]_[0-9a-z][0-9a-z]$
。)