BytePane

Essential Regex Patterns Cheat Sheet: 30+ Patterns Every Developer Needs

Text Processing16 min read

Why Every Developer Needs a Regex Cheat Sheet

Regular expressions are one of the most powerful tools in a developer's toolkit, but they are also one of the easiest to forget. You write a complex lookahead pattern on Monday, and by Friday you are staring at it wondering what it does. This cheat sheet gives you 30+ production-ready regex patterns that you can copy, paste, and adapt for real projects -- covering everything from email validation to log parsing.

Every pattern in this guide has been tested across JavaScript, Python, and Go. Where syntax differs between engines, the differences are noted. To test any of these patterns interactively, use our Regex Tester tool -- it highlights matches in real time and explains each part of your pattern.

Quick Reference: Regex Syntax Fundamentals

Before diving into specific patterns, here is a compact reference of the building blocks you will use in every regex.

SymbolMeaningExample
.Any character except newlinea.c matches "abc", "a1c"
^Start of string (or line with m flag)^Hello
$End of string (or line with m flag)world$
*0 or more of previousab*c matches "ac", "abc", "abbc"
+1 or more of previousab+c matches "abc", "abbc"
?0 or 1 of previous (optional)colou?r matches "color", "colour"
{n,m}Between n and m of previousa{2,4} matches "aa", "aaa", "aaaa"
[abc]Character class (any of a, b, c)[aeiou] matches any vowel
[^abc]Negated class (not a, b, or c)[^0-9] matches non-digits
\dDigit [0-9]\d+ matches "123"
\wWord character [a-zA-Z0-9_]\w+ matches "hello_world"
\sWhitespace (space, tab, newline)\s+ matches spaces between words
\bWord boundary\bcat\b matches "cat" not "catfish"
(abc)Capturing group(abc)+ matches "abcabc"
(?:abc)Non-capturing group(?:abc)+ groups without capturing

Email Validation Patterns

Email validation is the most common regex use case. The challenge is balancing strictness with practicality. The full RFC 5322 specification allows bizarre addresses like "spaces allowed"@example.com, but no real user enters those. Here are three patterns ranked by strictness.

Basic Email (covers 99% of cases)

// JavaScript
const emailBasic = /^[a-zA-Z0-9._%+-]+@[a-zA-Z0-9.-]+\.[a-zA-Z]{2,}$/;

emailBasic.test('[email protected]');      // true
emailBasic.test('[email protected]'); // true
emailBasic.test('@example.com');           // false
emailBasic.test('[email protected]');              // false

Strict Email (no consecutive dots, limited TLD)

// Prevents ".." in local part, requires 2-63 char TLD
const emailStrict = /^[a-zA-Z0-9](?:[a-zA-Z0-9._%+-]*[a-zA-Z0-9])?@[a-zA-Z0-9](?:[a-zA-Z0-9-]*[a-zA-Z0-9])?(?:\.[a-zA-Z0-9](?:[a-zA-Z0-9-]*[a-zA-Z0-9])?)*\.[a-zA-Z]{2,63}$/;

emailStrict.test('[email protected]');    // true
emailStrict.test('[email protected]');  // false (consecutive dots)
emailStrict.test('[email protected]');   // false (starts with dot)

HTML5 Email (browser standard)

// This is exactly what browsers use for <input type="email">
const emailHTML5 = /^[a-zA-Z0-9.!#$%&'*+/=?^_`{|}~-]+@[a-zA-Z0-9](?:[a-zA-Z0-9-]{0,61}[a-zA-Z0-9])?(?:\.[a-zA-Z0-9](?:[a-zA-Z0-9-]{0,61}[a-zA-Z0-9])?)*$/;

For production applications, the basic pattern is usually sufficient. The real validation happens when you send a confirmation email. Test these patterns in our Regex Tester with your own test addresses.

URL and Domain Patterns

URL with Protocol

// Matches http:// and https:// URLs
const url = /^https?:\/\/(?:www\.)?[a-zA-Z0-9-]+(?:\.[a-zA-Z]{2,})+(?:\/[^\s]*)?$/;

url.test('https://example.com');           // true
url.test('http://sub.example.co.uk/path'); // true
url.test('ftp://example.com');             // false (no ftp)
url.test('example.com');                   // false (no protocol)

Domain Name Only

// Matches domain names without protocol
const domain = /^(?:[a-zA-Z0-9](?:[a-zA-Z0-9-]{0,61}[a-zA-Z0-9])?\.)+[a-zA-Z]{2,}$/;

domain.test('example.com');       // true
domain.test('sub.example.co.uk'); // true
domain.test('-example.com');      // false (starts with hyphen)

URL Slug (Kebab Case)

// Matches URL-safe slugs like "my-blog-post"
const slug = /^[a-z0-9]+(?:-[a-z0-9]+)*$/;

slug.test('my-blog-post');    // true
slug.test('post123');         // true
slug.test('My-Post');         // false (uppercase)
slug.test('-leading-dash');   // false

URL encoding can add complexity to URL validation. If you are working with encoded URLs, check our URL Encoder/Decoder to understand how special characters are handled, and read our URL Encoding Guide for the full picture.

Password Strength Patterns

Password validation is best done with multiple checks rather than a single monolithic regex. However, a combined pattern is useful for client-side form validation.

Individual Checks (Recommended)

// Check each requirement separately for better error messages
const hasUppercase = /[A-Z]/;
const hasLowercase = /[a-z]/;
const hasDigit = /[0-9]/;
const hasSpecial = /[!@#$%^&*()_+\-=\[\]{};':"\\|,.<>\/?]/;
const minLength = /.{8,}/;

function validatePassword(password) {
  const errors = [];
  if (!hasUppercase.test(password)) errors.push('Need uppercase letter');
  if (!hasLowercase.test(password)) errors.push('Need lowercase letter');
  if (!hasDigit.test(password)) errors.push('Need a digit');
  if (!hasSpecial.test(password)) errors.push('Need a special character');
  if (!minLength.test(password)) errors.push('Need at least 8 characters');
  return errors;
}

Combined Pattern (All-in-One)

// Single regex: 8+ chars, 1 uppercase, 1 lowercase, 1 digit, 1 special
const strongPassword = /^(?=.*[a-z])(?=.*[A-Z])(?=.*\d)(?=.*[!@#$%^&*]).{8,}$/;

strongPassword.test('MyP@ss1!');    // true
strongPassword.test('weakpass');     // false (no upper, digit, special)
strongPassword.test('SHORT1!');     // false (less than 8 chars)

Need to generate strong passwords for testing? Our Password Generator creates cryptographically random passwords that satisfy any strength requirement. For hashing passwords securely after validation, see our Hash Functions guide.

IP Address Patterns

IPv4 Address

// Validates 0.0.0.0 to 255.255.255.255
const ipv4 = /^(?:(?:25[0-5]|2[0-4]\d|[01]?\d\d?)\.){3}(?:25[0-5]|2[0-4]\d|[01]?\d\d?)$/;

ipv4.test('192.168.1.1');    // true
ipv4.test('10.0.0.0');       // true
ipv4.test('256.1.1.1');      // false (256 > 255)
ipv4.test('192.168.1');      // false (only 3 octets)

IPv4 with CIDR Notation

// IPv4 + optional /0 to /32 subnet mask
const ipv4Cidr = /^(?:(?:25[0-5]|2[0-4]\d|[01]?\d\d?)\.){3}(?:25[0-5]|2[0-4]\d|[01]?\d\d?)(?:\/(?:3[0-2]|[12]?\d))?$/;

ipv4Cidr.test('10.0.0.0/8');       // true
ipv4Cidr.test('192.168.1.0/24');   // true
ipv4Cidr.test('10.0.0.0/33');      // false (max is /32)

Date and Time Patterns

ISO 8601 Date (YYYY-MM-DD)

// Basic format validation (doesn't check valid day/month combos)
const isoDate = /^\d{4}-(?:0[1-9]|1[0-2])-(?:0[1-9]|[12]\d|3[01])$/;

isoDate.test('2026-03-07');  // true
isoDate.test('2026-13-01');  // false (month 13)
isoDate.test('2026-1-1');    // false (needs zero-padding)

ISO 8601 DateTime with Timezone

// Matches: 2026-03-07T14:30:00Z, 2026-03-07T14:30:00+05:30
const isoDateTime = /^\d{4}-(?:0[1-9]|1[0-2])-(?:0[1-9]|[12]\d|3[01])T(?:[01]\d|2[0-3]):[0-5]\d:[0-5]\d(?:\.\d+)?(?:Z|[+-](?:[01]\d|2[0-3]):[0-5]\d)$/;

isoDateTime.test('2026-03-07T14:30:00Z');        // true
isoDateTime.test('2026-03-07T14:30:00+05:30');   // true
isoDateTime.test('2026-03-07T25:00:00Z');        // false (hour 25)

US Date Format (MM/DD/YYYY)

const usDate = /^(?:0[1-9]|1[0-2])\/(?:0[1-9]|[12]\d|3[01])\/\d{4}$/;

usDate.test('03/07/2026');  // true
usDate.test('12/31/2025');  // true
usDate.test('13/01/2026');  // false (month 13)

When working with Unix timestamps instead of date strings, our Timestamp Converter handles conversions between Unix epochs and human-readable formats.

Number and Currency Patterns

// Integer (positive or negative)
const integer = /^-?\d+$/;

// Decimal number (optional decimal part)
const decimal = /^-?\d+(?:\.\d+)?$/;

// Number with commas (US format: 1,234,567.89)
const numberWithCommas = /^-?\d{1,3}(?:,\d{3})*(?:\.\d+)?$/;

// US Currency ($1,234.56)
const usCurrency = /^\$\d{1,3}(?:,\d{3})*(?:\.\d{2})?$/;

// Percentage (0-100 with optional decimal)
const percentage = /^(?:100(?:\.0+)?|\d{1,2}(?:\.\d+)?)%$/;

// Hex number (0xFF, #FF)
const hexNumber = /^(?:0x|#)?[0-9a-fA-F]+$/;

// Scientific notation (1.23e-4, 5E10)
const scientific = /^-?\d+(?:\.\d+)?[eE][+-]?\d+$/;

For hex-to-decimal and other base conversions, use our Number Converter. For hex color codes specifically, try the Color Converter.

Phone Number Patterns

// US phone number (flexible format)
// Matches: (123) 456-7890, 123-456-7890, 123.456.7890, 1234567890
const usPhone = /^(?:\+1\s?)?(?:\(?\d{3}\)?[\s.-]?)?\d{3}[\s.-]?\d{4}$/;

usPhone.test('(555) 123-4567');   // true
usPhone.test('555-123-4567');     // true
usPhone.test('+1 555 123 4567'); // true
usPhone.test('5551234567');       // true

// International phone (E.164 format)
// Matches: +1234567890 to +123456789012345
const e164 = /^\+[1-9]\d{6,14}$/;

e164.test('+14155551234');   // true
e164.test('+442071234567');  // true
e164.test('+0123456789');    // false (starts with 0 after +)

Code and Development Patterns

Identifiers and Variables

// Valid variable name (most languages)
const variableName = /^[a-zA-Z_$][a-zA-Z0-9_$]*$/;

// camelCase
const camelCase = /^[a-z][a-zA-Z0-9]*$/;

// PascalCase
const pascalCase = /^[A-Z][a-zA-Z0-9]*$/;

// snake_case
const snakeCase = /^[a-z][a-z0-9]*(?:_[a-z0-9]+)*$/;

// SCREAMING_SNAKE_CASE (constants)
const screamingSnake = /^[A-Z][A-Z0-9]*(?:_[A-Z0-9]+)*$/;

// kebab-case (CSS classes, URLs)
const kebabCase = /^[a-z][a-z0-9]*(?:-[a-z0-9]+)*$/;

Semantic Versioning

// SemVer: MAJOR.MINOR.PATCH with optional pre-release and build
const semver = /^v?(?:0|[1-9]\d*)\.(?:0|[1-9]\d*)\.(?:0|[1-9]\d*)(?:-[\da-zA-Z-]+(?:\.[\da-zA-Z-]+)*)?(?:\+[\da-zA-Z-]+(?:\.[\da-zA-Z-]+)*)?$/;

semver.test('1.0.0');              // true
semver.test('v2.3.4');             // true
semver.test('1.0.0-alpha.1');      // true
semver.test('1.0.0+build.123');    // true
semver.test('1.0');                // false (missing patch)

UUID v4

// UUID v4 format: 8-4-4-4-12 hex characters
const uuidV4 = /^[0-9a-f]{8}-[0-9a-f]{4}-4[0-9a-f]{3}-[89ab][0-9a-f]{3}-[0-9a-f]{12}$/i;

uuidV4.test('550e8400-e29b-41d4-a716-446655440000'); // true
uuidV4.test('not-a-uuid');                            // false

// Any UUID version (v1-v5)
const anyUuid = /^[0-9a-f]{8}-[0-9a-f]{4}-[1-5][0-9a-f]{3}-[89ab][0-9a-f]{3}-[0-9a-f]{12}$/i;

Generate valid UUIDs instantly with our UUID Generator. For formatting JSON that contains UUIDs and other structured data, try the JSON Formatter.

HTML and Markup Patterns

// HTML tag (opening, closing, or self-closing)
const htmlTag = /<\/?[a-zA-Z][a-zA-Z0-9]*(?:\s+[a-zA-Z-]+(?:="[^"]*")?)*\s*\/?>/;

// Strip HTML tags (use with .replace())
const stripHtml = /<[^>]*>/g;
'<p>Hello <b>world</b></p>'.replace(stripHtml, '');
// "Hello world"

// HTML entity (named or numeric)
const htmlEntity = /&(?:#x?[0-9a-fA-F]+|[a-zA-Z]+);/;

// Hex color code (#RGB or #RRGGBB)
const hexColor = /^#(?:[0-9a-fA-F]{3}){1,2}$/;

// CSS class selector
const cssClass = /^\.[a-zA-Z_-][a-zA-Z0-9_-]*$/;

For working with HTML entities, our HTML Entities tool encodes and decodes named and numeric entities. For formatting messy HTML, use the HTML Formatter.

Advanced Patterns: Lookaheads and Lookbehinds

Lookaheads and lookbehinds let you assert that something exists before or after your match without including it in the result. They are essential for complex validation like password strength, or for extracting text that is surrounded by specific markers.

PatternNameMeaning
(?=...)Positive lookaheadFollowed by ...
(?!...)Negative lookaheadNOT followed by ...
(?<=...)Positive lookbehindPreceded by ...
(?<!...)Negative lookbehindNOT preceded by ...
// Extract price amount without the $ sign
const price = /(?<=\$)\d+(?:\.\d{2})?/g;
'Items: $19.99, $5.00, $120'.match(price);
// ["19.99", "5.00", "120"]

// Match "foo" only if NOT followed by "bar"
const notFollowedBy = /foo(?!bar)/g;
'foobar foobaz foo'.match(notFollowedBy);
// ["foo", "foo"] (matches foobaz and standalone foo)

// Match digits only if preceded by #
const afterHash = /(?<=#)\d+/g;
'Issue #123, PR #456, plain 789'.match(afterHash);
// ["123", "456"]

Log Parsing and Data Extraction Patterns

// Common Log Format (Apache/Nginx)
const logLine = /^(\S+) \S+ \S+ \[([^\]]+)\] "(\S+) (\S+) \S+" (\d{3}) (\d+|-)/;
const match = '127.0.0.1 - - [07/Mar/2026:14:30:00 +0000] "GET /api/users HTTP/1.1" 200 1234'.match(logLine);
// match[1] = "127.0.0.1" (IP)
// match[2] = "07/Mar/2026:14:30:00 +0000" (timestamp)
// match[3] = "GET" (method)
// match[4] = "/api/users" (path)
// match[5] = "200" (status)

// Extract key=value pairs
const keyValue = /([\w-]+)=(?:"([^"]*)"|([^\s,]+))/g;
const input = 'name="John Doe" age=30 city=NYC';
[...input.matchAll(keyValue)].map(m => ({ key: m[1], value: m[2] || m[3] }));
// [{ key: "name", value: "John Doe" }, { key: "age", value: "30" }, ...]

// JSON string value extraction
const jsonString = /"([^"\\]*(?:\\.[^"\\]*)*)"/g;

// Stack trace file:line extraction
const stackTrace = /at\s+(?:\S+\s+)?\(?([^:]+):(\d+):(\d+)\)?/g;

When parsing HTTP responses that contain status codes, our HTTP Status Codes reference helps decode what each code means. Read the full HTTP Status Codes Guide for in-depth explanations.

Search and Replace Patterns

// Remove extra whitespace
const multipleSpaces = /\s{2,}/g;
'too   many    spaces'.replace(multipleSpaces, ' ');
// "too many spaces"

// Trim leading/trailing whitespace (regex version of .trim())
const trim = /^\s+|\s+$/g;

// Convert camelCase to kebab-case
function camelToKebab(str) {
  return str.replace(/([a-z])([A-Z])/g, '$1-$2').toLowerCase();
}
camelToKebab('backgroundColor');  // "background-color"
camelToKebab('XMLParser');        // "x-m-l-parser" (careful!)

// Capitalize first letter of each word
function titleCase(str) {
  return str.replace(/\b\w/g, c => c.toUpperCase());
}
titleCase('hello world');  // "Hello World"

// Mask sensitive data (keep first/last 2 chars)
function maskEmail(email) {
  return email.replace(/^(.{2})(.*)(@.*)$/, (_, start, mid, end) =>
    start + '*'.repeat(mid.length) + end
  );
}
maskEmail('[email protected]');  // "jo******@example.com"

For case conversions without regex, our Case Converter handles camelCase, PascalCase, snake_case, kebab-case, and more with a single paste.

Cross-Language Regex Syntax Differences

FeatureJavaScriptPythonGo
Flags/pattern/gire.IGNORECASE(?i) inline only
Named groups(?<name>...)(?P<name>...)(?P<name>...)
LookbehindYes (variable length)Fixed length onlyNot supported
Backreferences\1\1Not supported (RE2)
Unicode property\p{L} (with u flag)Limited\p{L}

Go uses the RE2 engine, which guarantees linear-time matching but does not support backreferences or lookbehinds. If you need these features in Go, consider preprocessing with string operations. Python's re module supports most PCRE features but requires fixed-width lookbehinds. The newer regex third-party module supports variable-width lookbehinds.

Performance Tips for Regex

  1. Anchor your patterns -- Use ^ and $ when matching full strings. Without anchors, the engine tries the pattern at every position in the string.
  2. Be specific -- [0-9] is faster than . because the engine does not need to backtrack as often.
  3. Avoid catastrophic backtracking -- Patterns like (a+)+b cause exponential time on inputs like "aaaaaac". Use atomic groups or possessive quantifiers where available.
  4. Compile once, use many times -- In Python, use re.compile() for patterns used in loops. In JavaScript, define the regex outside the loop.
  5. Use non-capturing groups -- (?:...) is slightly faster than (...) when you do not need the captured value.
  6. Prefer string methods for simple tasks -- str.includes(), str.startsWith(), and str.endsWith() are faster than equivalent regex patterns.

Frequently Asked Questions

What is the best regex pattern for email validation?

For most applications, the pattern /^[a-zA-Z0-9._%+-]+@[a-zA-Z0-9.-]+\.[a-zA-Z]{2,}$/ provides a good balance between strictness and usability. It validates the general structure without being overly restrictive. The full RFC 5322 email regex is over 6,000 characters long and catches edge cases that rarely occur in practice. For production systems, validate with a simple regex first, then send a verification email to confirm it exists.

How do I make a regex case-insensitive?

Use the i flag after your regex pattern. In JavaScript: /pattern/i. In Python: re.compile(pattern, re.IGNORECASE) or the inline flag (?i) at the start. In Go, use the inline (?i) flag since Go does not support flags outside the pattern string. The flag makes every letter match both uppercase and lowercase.

What is the difference between .* and .*? in regex?

.* is greedy and matches as many characters as possible, while .*? is lazy (non-greedy) and matches as few characters as possible. Given the HTML <b>hello</b> <b>world</b>, the greedy <b>.*</b> matches the entire string from first to last tag, while lazy <b>.*?</b> matches each tag pair separately. Use lazy quantifiers when extracting the shortest possible match.

Test Your Regex Patterns Instantly

Paste any pattern from this cheat sheet into our free Regex Tester. It highlights matches in real time, shows capture groups, and explains every part of your expression.

Open Regex Tester

Related Articles