Regular expression for no more than two repeated letters/digits

I have a requirement to handle a regular expression for no more than two of the same letters/digits in an XSL file.

  • no space
  • does not support special chars
  • support (a-z,A-Z,0-9)
  • require one of a-z
  • require one of 0-9
  • no more than 2 same letter/digits (i.e., BBB will fail, BB is accepted)

What I have so far

(?:[^a-zA-Z0-9]{1,2})

Answers:

Answer

This regex will do it: ^(?!.*([A-Za-z0-9])\1{2})(?=.*[a-z])(?=.*\d)[A-Za-z0-9]+$

Here's the breakdown:

(?!.*([A-Za-z0-9])\1{2}) makes sure that none of the chars repeat more than twice in a row.

(?=.*[a-z]) requires at least one lowercase letter

(?=.*\d) requires at least one digit

[A-Za-z0-9]+ allows only letters and digits

EDIT : removed an extraneous .* from the negative lookahead

Answer

For matching the same character repeated 3 or more times consecutively, try:

([a-zA-Z0-9])\1{2,}

Sample matches (tested both here and here): AABBAA (no matches), AABBBAAA (matches BBB and AAA), ABABABABABABABA (no matches), ABCCCCCCCCCC (matches CCCCCCCCCC).

Answer

Does this one work for you?

/(\b(?:([A-Za-z0-9])(?!\2{2}))+\b)/

Try it out:

var regex = new RegExp(/(\b(?:([A-Za-z0-9])(?!\2{2}))+\b)/)
var tests = ['A1D3E', 'AAAA', 'AABAA', 'abccddeeff', 'abbbc', '1234']

for(test in tests) {
   console.log(tests[test] + ' - ' + Boolean(tests[test].match(regex)))
}

Will output:

A1D3E - true
AAAA - false
AABAA - true
abccddeeff - true
abbbc - false
1234 - true
Answer

You may do this in 2 regexes:

  1. /^(?=.*[a-z])(?=.*[0-9])[a-z0-9]+$/i This will assure that there is at least 1 digit and 1 letter while accepting only letters and digits (no space or special characters)
  2. /([a-z0-9])\1{2,}/i If this one is matched, then there is a repeated character. Which means you should throw false.

Explanation:

First regex:

  • ^ : match begin of line
  • (?=.*[a-z]) : check if there is at least one letter
  • (?=.*[0-9]) : check if there is at least one digit
  • [a-z0-9]+ : if the checks were true, then match only digits/letters one or more times
  • $ : match end of line
  • i : modifier, match case insensitive

Second regex:

  • ([a-z0-9]) : match and group a digit or a letter
  • \1{2,} : match group 1 two or more times
  • i : modifier, match case insensitive
Answer

In response to a clarification, it seems that a single regular expression isn't strictly required. In that case I suggest you use several regular expressions or functions. My guess is, performance isn't a requirement, since usually these sorts of checks are done in response to user input. User input validation can take 100ms and still appear to be instant, and you can run a lot of code in 100ms.

For example, I personally would do a check for each of your conditions in a separate test. First, check for spaces. Second, check for at least one letter. Next, check for at least one number. Finally, look for any spans of three or more repeated characters.

Your code will be much easier to understand, and it will be much easier to modify the rules later (which, experience has shown, is almost certainly going to happen).

For example:

function do_validation(string) {
    return (has_no_space(string) &&
            has_no_special_char(string) &&
            has_alpha(string) &&
            has_digit(string) &&
            ! (has_repeating(string)))

I personally consider the above to be orders of magnitude easier to read than one complex regular expression. Plus, adding or removing a rule doesn't make you have to reimplement a complex regular expression (and thus, be required to re-test all possible combinations).

Tags

Recent Questions

Top Questions

Home Tags Terms of Service Privacy Policy DMCA Contact Us

©2020 All rights reserved.