Skip to content

JavaScript Tutorial Regular Expressions

Regex Quantifiers and Groups

Lesson 96 of 258 2 min read By Deepak Paswan Updated Oct 4, 2026

Quantifiers: how many times

A quantifier goes right after the thing it repeats.

QuantifierMeaning
+one or more
*zero or more
?zero or one (optional)
{3}exactly 3
{2,4}between 2 and 4
{2,}2 or more
script.js
JS
console.log(/^\d+$/.test("12345"));      // → true
console.log(/^\d+$/.test(""));           // → false   (needs at least one)
console.log(/^\d*$/.test(""));           // → true    (zero or more)
console.log(/^colou?r$/.test("color"));   // → true    (u is optional)
console.log(/^\d{4}$/.test("2026"));     // → true    (exactly four digits)
console.log(/^\d{2,3}$/.test("1234"));   // → false

Greedy vs lazy

Quantifiers are greedy: they match as much as they can. Add ? to make them lazy (as little as possible).

script.js
JS
const html = "<b>bold</b> and <i>italic</i>";

console.log(html.match(/<.+>/)[0]);   // → <b>bold</b> and <i>italic</i>
console.log(html.match(/<.+?>/)[0]);  // → <b>

Groups: ( )

Parentheses group parts of a pattern so you can repeat them or capture them.

script.js
JS
console.log(/^(ab)+$/.test("ababab")); // → true

const match = "2026-03-15".match(/^(\d{4})-(\d{2})-(\d{2})$/);
console.log(match[1], match[2], match[3]); // → 2026 03 15

match[0] is the whole match, and match[1], match[2]… are the captured groups in order.

Named groups

Give groups names with (?<name>...) so you do not have to count.

script.js
JS
const { groups } = "2026-03-15".match(/^(?<year>\d{4})-(?<month>\d{2})-(?<day>\d{2})$/);
console.log(groups.year, groups.month, groups.day); // → 2026 03 15

Non-capturing groups

When you need grouping but not a capture, use (?:...).

script.js
JS
console.log(/^(?:https?):\/\//.test("https://example.com")); // → true

Backreferences

\1 refers to the first captured group. It can find repeated text.

script.js
JS
console.log(/\b(\w+) \1\b/.test("this is is a typo")); // → true
lightbulb
Keep it readable
A long pattern is easier to maintain when you break it into named pieces in JavaScript variables, or add a comment explaining what it matches.