You cannot apply quantifiers to anchors. Instead, to restrict the length of the input string, use a lookahead anchored at the beginning:
// ECMAScript (JavaScript, C++)
^(?=.{1,15}$)[a-zA-Z0-9]*[^$%^&*;:,<>?()"']*$
^^^^^^^^^^^
// Or, in flavors other than ECMAScript and Python
A(?=.{1,15}z)[a-zA-Z0-9]*[^$%^&*;:,<>?()"']*z
^^^^^^^^^^^^^^^
// Or, in Python
A(?=.{1,15})[a-zA-Z0-9]*[^$%^&*;:,<>?()"']*
^^^^^^^^^^^^^^^
Also, I assume you wanted to match 0 or more letters or digits with (a-z|A-Z|0-9)*
. It should look like [a-zA-Z0-9]*
(i.e. use a character class here).
Why not use a limiting quantifier, like {1,15}
, at the end?
Quantifiers are only applied to the subpattern to the left, be it a group or a character class, or a literal symbol. Thus, ^[a-zA-Z0-9]*[^$%^&*;:,<>?()"']{1,15}$
will effectively restrict the length of the second character class [^$%^&*;:,<>?()"']
to 1 to 15 characters. The ^(?:[a-zA-Z0-9]*[^$%^&*;:,<>?()"']*){1,15}$
will "restrict" the sequence of 2 subpatterns of unlimited length (as the *
(and +
, too) can match unlimited number of characters) to 1 to 15 times, and we still do not restrict the length of the whole input string.
How does the lookahead restriction work?
The (?=.{1,15}$)
/ (?=.{1,15}z)
/ (?=.{1,15})
positive lookahead appears right after ^
/A
(note in Ruby, A
is the only anchor that matches only start of the whole string) start-of-string anchor. It is a zero-width assertion that only returns true or false after checking if its subpattern matches the subsequent characters. So, this lookahead tries to match any 1 to 15 (due to the limiting quantifier {1,15}
) characters but a newline right at the end of the string (due to the $
/z
/
anchor). If we remove the $
/ z
/
anchor from the lookahead, the lookahead will only require the string to contain 1 to 15 characters, but the total string length can be any.
If the input string can contain a newline sequence, you should use [sS]
portable any-character regex construct (it will work in JS and other common regex flavors):
// ECMAScript (JavaScript, C++)
^(?=[sS]{1,15}$)[a-zA-Z0-9]*[^$%^&*;:,<>?()"']*$
^^^^^^^^^^^^^^^^^
// Or, in flavors other than ECMAScript and Python
A(?=[sS]{1,15}z)[a-zA-Z0-9]*[^$%^&*;:,<>?()"']*z
^^^^^^^^^^^^^^^^^^
// Or, in Python
A(?=[sS]{1,15})[a-zA-Z0-9]*[^$%^&*;:,<>?()"']*
^^^^^^^^^^^^^^^^^^