4

I would like to construct regular expression which will match password if there is no character repeating 4 or more times.

I have come up with regex which will match if there is character or group of characters repeating 4 times:

(?:([a-zA-Z\d]{1,})\1\1\1)

Is there any way how to match only if the string doesn't contain the repetitions? I tried the approach suggested in Regular expression to match a line that doesn't contain a word? as I thought some combination of positive/negative lookaheads will make it. But I haven't found working example yet.

By repetition I mean any number of characters anywhere in the string

Example - should not match

aaaaxbc

abababab

x14aaaabc

Example - should match

abcaxaxaz

(a is here 4 times but it is not problem, I want to filter out repeating patterns)

Community
  • 1
  • 1
mybrave
  • 1,662
  • 3
  • 20
  • 37

2 Answers2

1

That link was very helpful, and I was able to use it to create the regular expression from your original expression.

^(?:(?!(?<char>[a-zA-Z\d]+)\k<char>{3,}).)+$ 

or

^(?:(?!([a-zA-Z\d]+)\1{3,}).)+$
Preciel
  • 2,666
  • 3
  • 20
  • 45
Daniel Gimenez
  • 18,530
  • 3
  • 50
  • 70
  • Does not work for ´or group of characters´ OPs question. Put in your fiddle: blablablabla it will match. – Jorge Campos Dec 08 '13 at 15:59
  • Your examples seem to work perfectly. I will just update it to ^(?:(?!([a-zA-Z\d]+)\1{3,}).)+$ to support repetitions of more than one character. thanks – mybrave Dec 08 '13 at 16:17
  • I'd like you to explain what is the role of ``\k``, I don't understand it. I practice Python. Is it in another language ? – eyquem Dec 08 '13 at 17:01
  • Yeah it is other flavors to use named references. I just tend to do that when I do backreferences because I get confused otherwise. In python it's (?P=name) – Daniel Gimenez Dec 08 '13 at 17:28
  • You might want to update your answer to reflect the OP's request to avoid repetitions of multi-character sequences as well. – Peter Alfvin Dec 08 '13 at 22:04
0

Nota Bene: this solution doesn't answer exaactly to the question, it does too much relatively to the expressed need.

-----

In Python language:

import re

pat = '(?:(.)(?!.*?\\1.*?\\1.*?\\1.*\Z))+\Z'

regx = re.compile(pat)

for s in (':1*2-3=4@',
          ':1*1-3=4@5',
          ':1*1-1=4@5!6',
          ':1*1-1=1@',
          ':1*2-a=14#a~7&1{g}1'):
    m = regx.match(s)
    if m:
        print m.group()
    else:
        print '--No match--'

result

:1*2-3=4@
:1*1-3=4@5
:1*1-1=4@5!6
--No match--
--No match--

It will give a lot of work to the regex motor because the principle of the pattern is that for each character of the string it runs through, it must verify that the current character isn't found three other times in the remaining sequence of characters that follow the current character.
But it works, apparently.

eyquem
  • 26,771
  • 7
  • 38
  • 46