如何检查字符串是否包含小写字母,大写字母,特殊字符和数字?

2022-09-02 02:13:51

我一直在谷歌搜索,我没有找到我问题的答案:

如何使用正则表达式检查字符串是否至少包含以下每个字符串中的一个:

  • 大写字母
  • 小写字母
  • 数字
  • 特殊字符:~`!@#$%^&*()-_=+\|[{]};:'",<.>/?

所以我至少需要一个大写字母至少一个小字母至少一个数字至少一个特殊字符。

我相信答案很简单,但我找不到它。任何帮助都非常感谢。


答案 1

正则表达式不太适合需要满足所有几个条件的测试。

因此,最简单的答案不是尝试同时测试它们,而只是依次尝试四个类中的每一个。

您的代码可能会慢一些,但它将更容易阅读和维护,例如

public boolean isLegalPassword(String pass) {

     if (!pass.matches(".*[A-Z].*")) return false;

     if (!pass.matches(".*[a-z].*")) return false;

     if (!pass.matches(".*\\d.*")) return false;

     if (!pass.matches(".*[~!.......].*")) return false;

     return true;
}

编辑固定引号 - 一直在做太多该死的JS编程...


答案 2

这在java中作为单个正则表达式可以满足您的需求,尽管我个人会使用类似于Mark Rhodes提供的解决方案。这将变得荒谬很快(如果还没有......),因为规则变得更加复杂。

String regex = "^(?=.*?\\p{Lu})(?=.*?[\\p{L}&&[^\\p{Lu}]])(?=.*?\\d)" + 
               "(?=.*?[`~!@#$%^&*()\\-_=+\\\\\\|\\[{\\]};:'\",<.>/?]).*$"
  1. ^ 这与字符串的开头匹配。这并不是绝对必要的,但我发现它有助于可读性和理解。此外,当您经常可以进行重大性能改进并且几乎从不受到惩罚时,使用它。

  2. (?=X)这被称为积极的展望。基本上我们要说的是“字符串(^)的开头必须跟在这个东西X之后才能匹配,但不要将光标前进到X的末尾,停留在行的开头。(这是“向前看”的部分。

  3. .*?\p{Lu} 在行首后吃字符,直到找到大写字母。如果未找到大写字母,则此值将无法匹配。我们使用 \p{Lu} 而不是 A-Z,因为我们不希望来自世界其他地区的人举起双手抱怨我们的软件是由无知的美国人编写的。

  4. 现在我们回到行的开头(我们回去是因为我们使用了 lookahead),并开始搜索 .*?[\p{L}&[^\p{Lu}]] “所有字母,减去大写字母”的简写(因此匹配小写)。

  5. .*?\d + .*?['~!@#$%^&*()\-_=+\\\|\[{\]};:'\",<.>/?]对数字和特殊字符列表重复上述步骤。

  6. .*$ 匹配其他所有内容,直到行尾。我们这样做只是因为java中“matches”方法的语义,这些方法可以查看整个字符串是否与正则表达式匹配。你可以离开这部分,使用 Matcher#find() 方法,得到相同的结果。

  7. 《猫头鹰》是有史以来关于任何技术主题的最好的书之一。而且它既短又快,阅读速度快。我不能推荐它。