What are Capturing Groups?
Parentheses () in regex create a "capturing group". They do two things: they group part of the pattern together (so you can apply quantifiers to the whole group), and they capture the matched text so you can use it in your code.
Example: (\d{4})-(\d{2})-(\d{2}) matches a date like "2024-01-15" and captures the year, month, and day in separate groups.
Accessing Group Matches
In JavaScript: const m = str.match(/(\d{4})-(\d{2})-(\d{2})/) gives you m[1] = year, m[2] = month, m[3] = day.
Groups are numbered from left to right by their opening parenthesis, starting at 1 (index 0 is the full match).
Non-Capturing Groups
If you want to group without capturing, use (?:...). This is useful for applying a quantifier to a group without caring about the capture: (?:https?://)?example\.com — the https:// part is optional but not captured.
Named Capture Groups
Named groups use the syntax (?<name>...). They work like regular groups but you access matches by name instead of number:
(?<year>\d{4})-(?<month>\d{2})-(?<day>\d{2})
In JavaScript: m.groups.year, m.groups.month, m.groups.day.
Named groups make patterns self-documenting and much easier to maintain.
Backreferences
You can reference a captured group later in the same pattern using \1, \2, etc. (or \k<name> for named groups). This is useful for matching repeated content:
(['"])(.*?)\1 matches either single or double-quoted strings, ensuring the closing quote matches the opening quote.