0

I am trying to make a regex which will work for the XXXXRCYYYYMMDDnnnnnnnn string.

I tried

^[A-Z]{6}(?<!\\d)(?:(?:20\\d{2})(?:(?:(?:0[13578]|1[02])31)|(?:(?:0[1,3-9]|1[0-2])(?:29|30)))|(?:(?:20(?:0[48]|[2468][048]|[13579][26]))0229)|(?:20\\d{2})(?:(?:0?[1-9])|(?:1[0-2]))(?:0?[1-9]|1\\d|2[0-8]))(?!\\d){8}([\\d]{8}$

XXXXRC are 6 characters and YYYYMMDD is date and n's are any numbers.

This looks for first 6 character and then for YYYYMMDD and then look for 8 numbers.

It's not working.

B. Desai
  • 16,414
  • 5
  • 26
  • 47
Sunny
  • 14,522
  • 15
  • 84
  • 129
  • 2
    You should specify what you mean with your format string. What are the X, R, C, Y, M, D and n about? – Just a student Sep 21 '17 at 05:28
  • @Justastudent I edited the question. – Sunny Sep 21 '17 at 05:30
  • So, `XXXXRC` are all letters? Or just `[A-Z]`? And `n` are digits, `\d`? What's wrong with just having `\p{L}{6}\d{14}`? That would even support Unicode characters. – Just a student Sep 21 '17 at 05:35
  • 1
    I also need to validate date it should not be any invalida date like 1990/32/13 and year should be greater than 2015 – Sunny Sep 21 '17 at 05:39
  • 2
    That should have been in your question. Also, I'd like to **strongly** advise you not to do that validation in the regular expression. Instead, take the match and validate it separately. [Like so](https://stackoverflow.com/a/39649815/962603), for example. – Just a student Sep 21 '17 at 05:45

1 Answers1

1

Option 1:

Use capturing groups to break up the values, then check the values inside the capturing groups if they match a valid date:

^([\w]{4})([\w]{2})([0-9]{4})([0-9]{2})([0-9]{2})([0-9]{8})$

This will match something like: ABCDZY1999123101234567 into the following groups:

(ABCD)(ZY)(1999)(12)(31)(01234567)
^     ^   ^     ^   ^   ^
|     |   |     |   |   |
|     |   |     |   |   group 5
|     |   |     |   group 4
|     |   |     group 3
|     |   group 2
|     group 1 
group 0

In this case, groups 2, 3, and 4 would compose the date components. You can experiment and validate this regular expression through one of the many online RegEx testers, like regex101.com.

Option 2:

Take the above approach, but get more creative with the number capture groups to include only the date ranges desired. See Matching Numeric Ranges with a Regular Expression:

examples from the above site:

  • 000..255: ^([01][0-9][0-9]|2[0-4][0-9]|25[0-5])$
  • 0 or 000..255: ^([01]?[0-9]?[0-9]|2[0-4][0-9]|25[0-5])$
  • 0 or 000..127: ^(0?[0-9]?[0-9]|1[01][0-9]|12[0-7])$
  • 0..999: ^([0-9]|[1-9][0-9]|[1-9][0-9][0-9])$

However, this approach is very difficult to maintain and should only be used if you cannot use option 1 alone.

Kyle Falconer
  • 8,302
  • 6
  • 48
  • 68