如果某些值位于字符串中的特定位置,REGEXP将无法正确捕获某些名称


REGEXP not catching some names correctly if certain values are at certain positions in the string

我有以下regex,用于测试有效的名称格式:

^[a-zA-Z]+(([''','.'- ][a-zA-Z ])?[a-zA-Z]*)*$

它似乎可以很好地处理所有预期的奇怪名称的可能性,包括以下内容:

o'Bannon
Smith, Jr.
Double-barreled

当我把它插入我的PHP代码时,我遇到了问题。如果第一个字符是一个数字,它将作为有效字符通过。

如果最后一个字符是空格、逗号、句号或其他特殊允许的字符,则它将失败为无效字符。

我的PHP代码是:

$v = 'Tested Value';
$value = (filter_var($v, FILTER_VALIDATE_REGEXP,array("options"=>array("regexp"=>"^[a-zA-Z]+(([''','.'-,'  ][a-zA-Z ])?[a-zA-Z]*)*$^"))));
if (strlen($value) <2 && strlen($v) !=0) {
    return "not valid";
}

我在这里做错了什么?

^[a-zA-Z]+(([''','.'-,'  ][a-zA-Z ])?[a-zA-Z]*)*$^

正则表达式开头和结尾的插入符号(^(被解释为正则表达式的deliminator,而不是锚点。正则表达式并没有真正匹配字符串开头的数字,而是跳过它们,以便从找到的第一个字母开始匹配。您可以使用几乎任何ASCII标点符号作为正则表达式的分隔符,但大多数人使用#~,它们相对不常见,在正则表达式中没有特殊意义。

至于不允许在末尾使用标点符号,regex就是这样写的。具体来说,[''','.'- ][a-zA-Z ]要求每个撇号、逗号、句点或连字符后面都跟一个字母或空格。如果你真的想在结尾允许使用这些字符中的任何一个,这很简单:

~^(?:[a-z]+[',. -]*)+$~i

当然,对于验证名称来说,这不是一个特别好的正则表达式,但我没有什么比这更好的了;正则表达式特别不适合这项工作。你真的想告诉你的用户他们自己的名字是无效的吗?

您的正则表达式是复杂的方法

/^[a-z]+[',. a-z-]*$/i 

应该做同样的事情