The + quantifier: one or more, and when to prefer it
+ means one or more repetitions of the preceding token, and it is greedy. It is the quantifier to reach for whenever an empty match would be wrong.
At a glance
- Syntax
- +
- Equivalent to
- {1,}
- Greedy
- yes, the lazy form is +?
- Can match empty
- no, which is the point
- Applies to
- the single preceding token or group
- Unbounded
- yes, so a plus nested inside another quantifier is a backtracking risk
In detail
The difference between + and * is one character in the pattern and the entire meaning of a validator. /^\d+$/ rejects an empty string and /^\d*$/ accepts it, so a required field checked with the wrong one silently becomes optional. When in doubt about which to use, ask whether zero is a legitimate answer, and if it is not, the quantifier is a plus.
Like every quantifier it binds to the token immediately in front of it, which trips people writing repeated sequences. /ab+/ against "abab" returns two matches of ab, because the plus governs only the b. To repeat the pair you have to group it, and /(?:ab)+/ then returns the single match abab.
Being unbounded, a plus is one half of the recipe for catastrophic backtracking. On its own it is fine, and the engine matches a run of characters in linear time. Nested inside another quantifier over the same characters, as in (a+)+, the number of ways to divide the input grows exponentially and a long string of a characters will hang the evaluation.
In a delimited scan a plus over a negated class is usually the right structure. [^"]+ inside quotes says exactly what it means, requires at least one character, and does not backtrack the way a lazy dot does. That combination is faster to run and considerably easier to read six months later.
Examples
/^\d+$/.test(""); // false
/^\d*$/.test(""); // true
/^\d+$/.test("42"); // true"abab".match(/ab+/g); // ["ab", "ab"]
"abab".match(/(?:ab)+/g); // ["abab"]The plus in the first pattern applies to the b alone.
Things that catch people out
- Using * where + belonged turns a required field into an optional one, and the test suite passes because every fixture has a value in it.
- /ab+/ repeats the b, not the pair. Grouping is required to repeat a sequence, and a non capturing group keeps the numbering stable.
- A plus inside a group that is itself quantified is the standard catastrophic backtracking shape. Bound one of the two or make the branches disjoint.
Try it: Regex Tester
Type a pattern and a test string, watch every match highlight as you go, read a plain English breakdown of each token, and check the numbered and named groups it captured.
Regex Tester
LOCAL · Browser-OnlyTest and debug regular expressions with live matching and highlights
Related Regex syntax
All regex syntax →The * quantifier: zero or more, including nothing at all
The star quantifier succeeds even when it matches nothing, which is why a global match against it returns an empty string at almost every position.
{n}: matching exactly n repetitions
An exact count is the clearest quantifier there is, until it is applied to a group, at which point the capture keeps only the final iteration.
(?:...): grouping without creating a capture
A non capturing group applies quantifiers and alternation without taking a number, which is what keeps $1 pointing at the same thing after an edit.
The ? quantifier: optional, and its two other jobs
A question mark after a token makes it optional. The same character also marks a lazy quantifier and opens a special group, which is why patterns look dense.
{n,}: at least n repetitions, with no upper bound
The open ended count covers everything * and + cannot express, and a stray space after the comma turns the whole quantifier into literal text.
{n,m}: bounded repetition between two counts
A bounded count is inclusive at both ends and greedy toward the maximum. JavaScript has no {,m} shorthand, and writing one produces literal text.
Tools for this
- Regex Tester Free online regex tester - test and debug regular expressions with live matching and highlights
- Regex Playground Regex playground with live match highlighting, named groups, find and replace, and shareable links