Positive and Negative Lookahead: Consecutive Numbers

Tell us what’s happening:
I’m stuck on writing for two-consecutive numbers. I had thought that adding + to /d would work but it created an error. I’ve finagled with other variations of this idea, but I can’t get past the notion that /d{2} should work. I need help.

Your code so far


let sampleWord = "astronaut";
let pwRegex = /(?={>5})(?=\d{2})/; // Change this line
let result = pwRegex.test(sampleWord);

Your browser information:

User Agent is: Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/68.0.3440.106 Safari/537.36.

Link to the challenge:
https://learn.freecodecamp.org/javascript-algorithms-and-data-structures/regular-expressions/positive-and-negative-lookahead/

So the way you use quantifiers is {n,m}, and if you leave m out, it gets an upper limit of infininity. {>5} is not valid, but {6,} is — and means the same thing. So you should probably correct it.

As for your idea of using \d{2}. This is perfect! The RegEx engine, however, is looking for a particular point where there are 6 characters ahead of it, and 2 digits ahead of it.

This won’t match all the test cases. For example, abcd12. The point just before “12” has two digits ahead. But it doesn’t have 6 characters ahead.

Instead, try to get it to match at the beggining of the string. This means you need to allow characters before the occurrence of two digits.

Try changing

\d{2}

(which, by the way, is not causing the error.) to

.*\d{2}

If you’ve changed {>5} to {6,} too — your regular expression should start working.

It worked. Thank you for very much. I just wanted to clarify that the reason .*\d{2}. My understanding is that in conjunction * and . add valence to the preceding elements and allow \d to do work on the remaining two spots of the password. However, is this correct? Also, if it is, could you say it in a better way using the proper discourse.

I might be completely mistaken, but: let’s say our password is

abcd12

.test() is trying to find a match at a particular point. We need to satisfy two conditions at that point

  • there are six characters immediately ahead
  • there are two numbers immediately ahead
 a b c d 1 2
^
 | | | | | |    Six characters (yes)
 _ _            Numbers (no)

Note that to get the number condition to match, we have to:

 a b c d 1 2
        ^
         | | | | | |    Six characters (no)
         _ _            Numbers (yes)

So there’s no way to get both conditions to be satisfied at the same place.

We need to change our conditions.

  • Six characters immediately ahead
  • Some set of characters (0 or more) followed by two digits

Note that . is any character, and * is “0 or more”, so together they mean “0 or more characters”.

Now let’s try to find a point where this stuff matches.

 a b c d 1 2
        ^
         | | | | | |    Six characters (no)
         _ _            Numbers (yes)
 a b c d 1 2
    ^
     | | | | | |    Six characters (no)
     . . _ _           Numbers (yes)

Note that now, our numbers condition will match anywhere. Can we find a place where our six character condition passes?

 a b c d 1 2
^
 | | | | | |    Six characters (yes)
 . . . . _ _            Numbers (yes)

Indeed we can. And therefore both conditions now pass at the same place, so a match is found, and the test passes. Remember that (?= does not mean “if”, it means “there is”. It’s asserting what must be at that particular point – and so both have to be matching the same place.