Guida rapida Regex gratuita
Guida di riferimento interattiva per le espressioni regolari.
Testa un pattern
Come usare
- Sfoglia le categorie di pattern o usa la casella di ricerca per trovare pattern specifici.
- Inserisci un'espressione regolare nel campo «Testa un pattern» e del testo di esempio in «Testo di test».
- Attiva/disattiva i flag (globale, insensibile a maiuscole/minuscole, multilinea) e visualizza le corrispondenze evidenziate istantaneamente.
Domande frequenti
Cos'è un'espressione regolare?
Un'espressione regolare (regex o regexp) è un pattern usato per trovare, cercare e sostituire del testo. Usa caratteri e una sintassi speciali per definire le stringhe da trovare.
A cosa servono i flag?
Globale (g) trova tutte le corrispondenze. Insensibile alla maiuscole/minuscole (i) ignora la differenza tra maiuscole e minuscole. Multilinea (m) tratta ^ e $ come limiti di riga invece che limiti di stringa.
Posso usare questo cheatsheet nel mio codice?
Sì! Una volta testato un pattern qui e verificato che funziona, copia il pattern regex direttamente nel tuo codice JavaScript, Python o in un altro linguaggio di programmazione.
Breve storia del linguaggio dei pattern
Le espressioni regolari sono nate come un pezzo di informatica teorica. Stephen Kleene definì gli "insiemi regolari" in un articolo del 1956 sulle reti neurali; Ken Thompson le portò in Unix nel 1968 con grep. La libreria regex open source di Henry Spencer (metà degli anni Ottanta) divenne la base di molte implementazioni successive. Larry Wall estese drasticamente la sintassi in Perl, e le sue "Perl-compatible regular expressions" (PCRE) sono diventate lo standard di fatto seguito dalla maggior parte dei linguaggi moderni. Oggi esistono diverse varianti di regex strettamente imparentate ma sottilmente diverse, e un pattern che funziona in un motore non sempre funziona in modo identico in un altro.
Il motore in cui vive il tuo pattern
La stessa sintassi può significare cose diverse in motori diversi. Le grandi famiglie:
- POSIX BRE (Basic Regular Expressions), usate dalla modalità predefinita di
grepe dased. Molti metacaratteri richiedono l'escape con backslash:(,),{,},+,?,|sono letterali se non vengono preceduti da backslash. - POSIX ERE (Extended Regular Expressions), usate da
egrepeawk. I metacaratteri sopra elencati funzionano senza escape. - PCRE (Perl-Compatible Regular Expressions), estende ERE con lookaround, gruppi atomici, cattura con nome e backreference. Usato da PHP e dalla maggior parte dei linguaggi moderni. Le abbreviazioni di classe derivate da Perl
\d,\w,\ssono comuni a PCRE, JavaScript, .NET, Java e Python. - JavaScript RegExp, vicino a PCRE ma con differenze importanti. ES2018 ha aggiunto i lookbehind, i gruppi di cattura con nome, il flag dotall
se le proprietà Unicode tramite il flagu. Il flagvper la notazione di insiemi è arrivato con ES2024. - Python
ree Pythonregex,reè nella libreria standard; il modulo di terze partiregexaggiunge funzionalità sensibili a Unicode, lookbehind a larghezza variabile e altri miglioramenti in stile PCRE. - RE2 (libreria di Google, usata in Go), garantisce tempo lineare ma non supporta backreference né lookaround. Il compromesso: prestazioni prevedibili, meno funzionalità.
Il tester interattivo di questo cheatsheet gira in JavaScript, quindi il pattern è valutato dal motore JS del browser. Pattern che funzionano qui possono comportarsi diversamente in Python o PHP. La maggior parte delle differenze riguarda funzionalità avanzate (lookbehind, escape di proprietà Unicode, backreference) piuttosto che la sintassi di base.
I mattoni fondamentali
Quasi ogni pattern regex è costruito a partire da questi elementi:
- Letterali, corrispondono a sé stessi.
catcorrisponde alla sottostringa "cat". - Ancore,
^(inizio della stringa o riga),$(fine),\b(confine di parola),\B(non confine di parola). - Classi di caratteri,
[abc]corrisponde a a, b o c.[^abc]nega.[a-z]è un intervallo. Abbreviazioni:\d(cifra),\w(carattere di parola: lettera, cifra, trattino basso),\s(spazio bianco), e versioni in maiuscolo per la negazione (\D,\W,\S). - Quantificatori,
?(0 o 1),*(0 o più),+(1 o più),{n},{n,},{n,m}. Greedy per impostazione predefinita (corrispondono al massimo possibile); aggiungi?per essere lazy:*?,+?,??. - Gruppi,
(...)di cattura,(?:...)non di cattura,(?<name>...)con nome (PCRE, JS, Python). - Alternanza,
cat|dogcorrisponde a uno dei due. - Lookaround,
(?=...)lookahead positivo,(?!...)lookahead negativo,(?<=...)lookbehind positivo,(?<!...)lookbehind negativo. Corrispondono senza consumare caratteri. - Riferimenti all'indietro,
\1,\2(numerati),\k<name>(con nome). Corrispondono allo stesso testo già catturato dal gruppo corrispondente. - Flag,
g(globale),i(senza distinzione maiuscole/minuscole),m(multilinea:^e$corrispondono ai confini di riga),s(dotall:.corrisponde anche ai newline),u(Unicode),y(sticky in JS).
Pattern che vale la pena memorizzare
Alcuni pattern compaiono così spesso che vale la pena tenerli a mente:
| Uso | Pattern |
|---|---|
| Email (base) | ^[a-zA-Z0-9._%+-]+@[a-zA-Z0-9.-]+\.[a-zA-Z]{2,}$ |
| URL | https?://[^\s]+ |
| Numero di telefono statunitense | \(?\d{3}\)?[-.\s]?\d{3}[-.\s]?\d{4} |
| Data ISO (AAAA-MM-GG) | \d{4}-(0[1-9]|1[0-2])-(0[1-9]|[12]\d|3[01]) |
| Indirizzo IPv4 (senza validazione degli ottetti) | \b\d{1,3}\.\d{1,3}\.\d{1,3}\.\d{1,3}\b |
| Colore esadecimale | ^#?([0-9a-fA-F]{3}|[0-9a-fA-F]{6})$ |
| Spazi all'inizio o alla fine di una riga | ^\s+|\s+$ |
| Più spazi consecutivi | \s{2,} |
Una nota sulla regex per email: la validazione completa secondo RFC 5322 richiede una regex mostruosa di 6.000 caratteri. La forma semplice qui sopra accetta il 99% degli indirizzi reali e non rifiuta nulla di legittimo; in produzione, invia un'email di conferma invece di cercare di validare perfettamente la sintassi.
Greedy contro lazy: una sorpresa frequente
Per impostazione predefinita, i quantificatori sono greedy: corrispondono al massimo possibile pur consentendo al pattern complessivo di corrispondere. Quindi <.+> applicato a <a>text</a> corrisponde all'intera stringa, non solo a <a>, perché .+ afferra quanto più può. Per corrispondere alla stringa più piccola possibile, aggiungi ? al quantificatore: <.+?> corrisponde a <a> e poi a </a> separatamente. La scelta greedy/lazy è una delle cause più comuni di bug del tipo "perché la mia regex non corrisponde a quello che mi aspettavo".
Backtracking catastrofico e ReDoS
Alcuni pattern regex possono richiedere tempo esponenziale per fallire su certi input, una classe di vulnerabilità denial-of-service chiamata ReDoS (Regular Expression Denial of Service). I colpevoli classici sono quantificatori annidati come (a+)+ oppure (a|aa)+ applicati a una lunga stringa di a seguita da un carattere non corrispondente. Il motore prova ogni modo possibile di dividere la stringa prima di arrendersi, e il numero di modi è esponenziale.
Incidenti reali: il blackout di Cloudflare del 2019 fu causato da una regex usata in una regola WAF che subì un backtracking catastrofico su certi input. Stack Overflow ebbe un incidente simile nel luglio 2016: una regex di trim (^[\s]+|[\s]+$) incappò in backtracking esponenziale su un singolo commento contenente circa 20.000 caratteri di spaziatura consecutivi e mise offline il sito per 34 minuti. Abitudini difensive: evita i quantificatori annidati, preferisci i gruppi atomici ((?>...)) dove sono supportati e considera l'uso di RE2 o motori a tempo lineare per input non fidati.
Stranezze per linguaggio che vale la pena conoscere
- JavaScript: i backslash richiedono il doppio escape nei letterali stringa (
"\\d") ma non nei letterali regex (/\d/). Quando possibile, usa la forma letterale regex. - Python: usa stringhe grezze (
r"\d+") per evitare problemi con i backslash. Il moduloreè nella libreria standard;regexsu PyPI aggiunge funzionalità extra. - Java: i backslash richiedono il quadruplo escape (
"\\\\d"per\d) perché i letterali stringa Java usano\come escape e il compilatore regex poi vede\\d. - Bash: il matching regex in
[[ string =~ pattern ]]usa POSIX ERE. Le regole di quoting sono delicate; consultaman bash. - Go: usa RE2, quindi backreference e lookaround non sono disponibili. Compromesso: garanzia di tempo lineare.
Quando NON usare le regex
La famosa frase di Jamie Zawinski del 1997: "Alcuni, di fronte a un problema, pensano: 'lo so, userò le espressioni regolari'. Ora hanno due problemi."
- Non analizzare HTML o XML con la regex. Usa un parser vero (DOMParser nei browser, BeautifulSoup in Python, jsoup in Java, ecc.). La struttura annidata di HTML è fondamentalmente al di là di ciò che la regex può esprimere in modo pulito.
- Non analizzare JSON con la regex. Usa JSON.parse o i parser JSON della libreria standard.
- Non validare le email rigorosamente con la regex. Invia un'email di conferma; è l'unica verifica affidabile.
- Non scrivere un parser CSV come regex. Campi tra virgolette con virgole incorporate, virgolette di escape e valori su più righe superano rapidamente ciò che la regex può gestire in modo pulito.
- Non cercare di abbinare parentesi bilanciate. La regex standard non può (è un linguaggio context-free); alcuni motori PCRE hanno funzionalità di ricorsione che imbrogliano, ma un parser vero è più pulito.
Errori comuni
- Dimenticare di fare l'escape dei caratteri speciali.
.,*,?,+,(,),[,],{,},\,^,$,|,/hanno tutti significati speciali. Per cercarli letteralmente, fai precedere il backslash. - Quantificatori greedy che consumano troppo. Aggiungi
?per il matching lazy quando vuoi la corrispondenza più piccola possibile. - Dimenticare il flag global e chiedersi perché compare solo la prima corrispondenza.
String.prototype.match()di JavaScript restituisce solo la prima corrispondenza senza il flagg. - Backtracking catastrofico su input lunghi. Quantificatori annidati come
(a+)+possono bloccarsi su certi input. Testa con casi limite. - Dare per scontato che la stessa regex si comporti allo stesso modo in ogni linguaggio. Lookbehind, escape Unicode e abbreviazioni delle classi di caratteri variano tutti.
- Validare le email in modo troppo rigoroso. La regex tecnicamente corretta secondo RFC 5322 è impossibile da mantenere; una regex semplice più email di conferma alla registrazione è il pattern che funziona.
- Usare regex su HTML, JSON o CSV. Usa un parser dedicato; il tempo che risparmi all'inizio lo perdi in bug.
Altre domande frequenti
Perché il mio pattern funziona qui ma fallisce nel mio codice?
La causa più comune sono le differenze tra motori. RegExp di JavaScript non supporta alcune funzionalità di PCRE (e viceversa). Trappole comuni: i lookbehind sono stati aggiunti tardi a JS (ES2018), la sintassi dei gruppi con nome differisce leggermente, gli escape di proprietà Unicode richiedono il flag u e le classi POSIX come [[:alpha:]] sono per lo più assenti da JS. Testa nel motore di destinazione.
Esiste un modo "globale" per cercare attraverso più righe?
Due flag lavorano insieme. Il flag m (multilinea) fa sì che ^ e $ corrispondano all'inizio e alla fine di ogni riga anziché dell'intera stringa. Il flag s (dotall) fa sì che . corrisponda anche ai newline. Combinati con g per il globale, puoi scrivere pattern che attraversano più righe e trovano ogni corrispondenza: /^foo.+$/gms.
I miei pattern e il testo di prova vengono inviati da qualche parte?
No. Il matching del pattern usa il motore RegExp JavaScript integrato nel browser; nulla viene caricato su nessun server. Questo è importante quando testi pattern su dati di log di produzione reali, risposte di API interne o contenuti sensibili.
Dovrei imparare i lookbehind?
Utili ma non essenziali. I lookbehind ti permettono di trovare testo preceduto da qualcosa senza includere quel qualcosa nella corrispondenza. Esempio: (?<=\$)\d+ corrisponde alle cifre dopo un simbolo del dollaro senza consumare il dollaro. Sono supportati in PCRE, nel JavaScript moderno (ES2018+) e nel modulo regex di Python. Se scrivi pattern portabili, controlla prima il motore di destinazione.
Perché usare (?:...) invece di (...)?
I gruppi non di cattura ((?:...)) sono leggermente più veloci, non occupano uno slot nell'array delle catture e mantengono i risultati puliti. Usali quando hai bisogno di raggruppare per alternanza o quantificazione ma non devi estrarre il testo trovato. (http|https):// crea una cattura di cui forse non hai bisogno; (?:http|https):// no.
Qual è il modo corretto di cercare caratteri Unicode?
In JavaScript, aggiungi il flag u e usa gli escape delle proprietà Unicode: /\p{Letter}+/gu corrisponde a sequenze di lettere in qualsiasi alfabeto. Senza il flag u, \w corrisponde solo ai caratteri ASCII di parola. Il modulo re di Python è consapevole di Unicode per impostazione predefinita in Python 3. Java richiede Pattern.UNICODE_CHARACTER_CLASS. La maggior parte dei motori ha un modo per essere consapevole di Unicode; controlla la documentazione del tuo.