0

嗨,非常有趣的正则表达式,我尝试了很多时间,但有些困难。正则表达式规则:

  1. 用户可以使用以下全小字符([az])、全大写([AZ])、数字([0-9])和以下符号
    !~*:;<>+#-£$&_?(){ }[] 和一个空格。所有字符的顺序不限,但限制如下:
  2. 输入不能以数字开头。

  3. 用户可以在输入中的任何位置使用零个或一个空格,但输入不能以空格开头和结尾。

  4. 输入必须包含至少一个特殊的后续字符!~*:;<>+#-£$&_?(){}[] 以任意顺序。
  1. 输入长度在 6-15 之间。问题:满足上述要求的正则表达式。我花了很多时间在上面。但是做下面的正则表达式。

正则表达式='/^([a-zA-Z]|!|\~|*|\:|\;|\<|>|+|#|-|\£|\$|\&|_|\ ?|{|}|[|]|(|)){1,20}(\s){0,1}([a-zA-Z]|!|\~|*|\:|\;| \<|>|+|#|-|\d|\£|\$|\&|_|\?|{|}|[|]|(|)){1,20}(!|\~ |*|\:|\;|\<|>|+|#|-|\£|\$|\&|_|\?|{|}|[|]|(|)){1,} $/i'; 它满足所有规则,但不满足第 4 条规则。

满足上述规则的完整正则表达式将不胜感激。

4

3 回答 3

2

在找到解决方案之前的一些提示。

  1. 您使用修饰符i,表示“大小写无关”匹配。所以a-zA-Z不需要只使用a-zor A-Z

  2. 从您的角色列表中[a-zA-Z]|!|\~|*|\:|\;|\<|>|+|#|-|\£|\$|\&|_|\?|{|}|[|]|(|)

    1. 有些字符需要转义,因为它们在正则表达式中很特殊。

    2. 跳过交替并将所有字符放在 char 类中(你也可以避免转义)

  3. 要执行某些规则,您需要先行断言

所以你的正则表达式(用于 php)看起来像:

^(?![\d ])(?![^ ]*[ ][^ ]*[ ])(?=.*[!~*:;<>+#\-£$&_?{}\[\]()])[a-z\d!~*:;<>+#\-£$&_?{}\[\]() ]{6,15}(?<![ ])$

如果您需要JavaScript 的正则表达式,则不能使用后向断言。您也可以通过前瞻来替换它:

^(?![\d ])(?!.* $)(?![^ ]*[ ][^ ]*[ ])(?=.*[!~*:;<>+#\-£$&_?{}\[\]()])[a-z\d!~*:;<>+#\-£$&_?{}\[\]() ]{6,15}$

在 Regexr 上看到它(注意。我在那里使用过 [^ \r])只是因为我需要多行进行测试)

正则表达式解释:

  • [a-z\d!~*:;<>+#\-£$&_?{}\[\]() ]{6,15}以所需的长度匹配您希望允许的所有字符。

  • (?![\d ]) 负前瞻断言,确保字符串不以数字或空格开头。

  • (?![^ ]*[ ][^ ]*[ ]) 负前瞻断言,确保字符串不超过一个空格

  • (?=.*[!~*:;<>+#\-£$&_?{}\[\]()]) 积极的前瞻断言,确保字符串确实具有您的特殊符号之一

  • (?<![ ])$ 否定后向断言,确保字符串不以空格结尾。

统一码:

JavaScript 本身不支持这个!

如果您想支持 Unicode 字母而不是仅支持旧的 ASCII 字母,请替换 [a-z]\p{L}. 然后您还可以删除i修饰符,因为\p{L}它是一个Unicode 属性,可以匹配任何语言中的所有字母(只有完整的字母,而不是组合字母,您可以使用[\p{L}\p{Mn}\p{Mc}]

于 2013-06-18T06:00:33.470 回答
0

就像@Juhana 在评论中所建议的那样,为什么不单独测试你的规则而不是制作一个过于复杂的正则表达式呢?像这样的东西。(这些不是实际的解决方案或经过测试,因为您没有提供任何测试字符串,更多的是如何以不同方式思考您的问题的示例)

Javascript

function verify(string) {
    var length = string.length;

    if (length < 6 || length > 15 || /^\d/.test(string) || /^\s/.test(string) || /\s$/.test(string) || /\s\s/.test(string) || /[!~*:;<>+#-£$&_?(){}[\]]+/.test(string)) {
        return false;
    }

    return true;
}

PHP

function verify($string) {
    $length = strlen($string);

    if ($length < 6 || $length > 15 || preg_match("/^\d/", $string) || preg_match("/^\s/", $string) || preg_match("/\s$/", $string) || preg_match("/\s\s/", $string) || preg_match("/[!~*:;<>+#-£$&_?(){}[\]]+/", $string)) {
        return false;
    }

    return true;
}
于 2013-06-18T07:11:23.893 回答
0

这就是我的做法。

<?php
    $symbols = '!~*:;<>+#\-£$&_?(){}\[\]';
    $regex = "/^(?=.*[$symbols])(?=.{6,15}\$)(?!.*  )[a-zA-Z][a-zA-Z0-9 $symbols]+[a-zA-Z0-9]$";
?>

如果以下任何解释不清楚,请参考他们的号码询问:

  1. 请注意,为方便起见,我们已将符号列表分解。
  2. 请注意,我们已经转义了-,[], 因为这些是字符类中有意义的字符。只要是在开头或结尾,并且在开头,就可以逃避它们,但是由于我们正在与其他字符混合,我们无法确定“开头”或“结尾”到底在哪里是。-]$symbols
  3. (?=...)被称为前瞻。它们对于断言多个条件很有用。例如,(?=.*[$symbols])断言某处有一个符号(因此是.*);并且(?=.{6,15}\$)断言,从头到尾,字符串的长度在 6 到 15 个字符之间(请注意,$转义只是因为它存在于双引号中)。
  4. (?!...)称为负前瞻。断言在(?!.* )任何地方都没有两个连续的空格。
  5. 其余的应该是显而易见的。
于 2013-06-18T05:47:59.297 回答