Sintaxa expresiilor regulate
Definirea claselor de caractere
Pentru a defini expresii regulate, putem utiliza clase de caractere. Pentru a defini o clasă de caractere, se folosesc paranteze pătrate:
- [xyz] (potrivire alternativă): se potrivește cu unul dintre caracterele: x, y sau z (analog x|y|z)
- [^xyz] (negare): se potrivește cu textul care conține orice caracter, CU EXCEPȚIA lui x, y sau z
- [a-zA-Z] (interval): se potrivește cu orice caracter din intervalul a-z sau A-Z
De exemplu, să verificăm dacă în text există caracterele "a", "b" sau "c":
const exp = /[abc]/; // corespunde ori "a", ori"b", ori"c"
const str1 = "JavaScript";
const str2 = "Pascal";
const str3 = "Python";
console.log(exp.test(str1)); // true
console.log(exp.test(str2)); // true
console.log(exp.test(str3)); // false
Expresia [abc] indică faptul că șirul trebuie să conțină una dintre cele trei litere. Expresia "[abc]" este echivalentă cu expresia "a|b|c".
Să luăm un exemplu mai practic. Presupunem că avem coduri PIN de 4 cifre și dorim să verificăm dacă codul PIN conține doar cifre:
const exp = /[0-9][0-9][0-9][0-9]/; // se potrivește cu patru cifre consecutive
const code1 = "1234";
const code2 = "jav5";
const code3 = "3452";
console.log(exp.test(code1)); // true
console.log(exp.test(code2)); // false
console.log(exp.test(code3)); // true
Expresia [0-9][0-9][0-9][0-9] se potrivește cu orice secvență de 4 cifre consecutive. De exemplu, șirul "3452" se potrivește acestui șablon, dar NU se potrivește șirul "jav5" (aici există doar o cifră). Șirul "jav5" ar corespunde șablonului "[a-z][a-z][a-z][0-9]" (primele trei caractere alfabetice mici, urmate de o cifră).
Este important de menționat că expresia [0-9][0-9][0-9][0-9] nu este optimă și vom explora cum o putem simplifica mai jos.
Un alt exemplu aplică negarea:
const exp = /[^a-z]/; // se potrivește cu orice caractere, în afară de caracterele din intervalul a-z
const code1 = "zorro";
const code2 = "zorro5";
const code3 = "34521";
console.log(exp.test(code1)); // false
console.log(exp.test(code2)); // true
console.log(exp.test(code3)); // true
Aici, șirurile sunt verificate în funcție de expresia "[^a-z]", care se potrivește cu orice caractere, în afara intervalului "a-z". De exemplu, șirul "zorro" NU se potrivește acestei expresii. Cu toate acestea, șirul "zorro5" se potrivește, deoarece conține un caracter care nu aparține intervalului "a-z".
Dacă este necesar, putem combina expresii:
const exp = /[bs]un/; // se potrivește cu șirurile "bun" și "sun"
const str1 = "bunătate";
const str2 = "lumină";
const str3 = "sunt";
console.log(exp.test(str1)); // true
console.log(exp.test(str2)); // false
console.log(exp.test(str3)); // true
Expresia [bs]un indică șirurile care pot conține subșirurile "bun" și "sun".
Metacaractere
În loc să definim clasele noastre de caractere, putem utiliza cele încorporate, numite și metacaractere - caractere care au un sens specific:
- \d: se potrivește oricărei cifre de la 0 la 9. Echivalent cu expresia [0-9]
- \D: se potrivește oricărui caracter care nu este o cifră. Echivalent cu expresia [^0-9]
- \w: se potrivește oricărei litere, cifre sau caracterului de underscore (în intervalul A–Z, a–z, 0–9). Echivalent cu expresia [a-zA-Z_0-9]
- \W: se potrivește oricărui caracter care nu este o literă, cifră sau caracterul de underscore (adică nu se găsește în intervalele A–Z, a–z, 0–9). Echivalent cu expresia [^\w]
- \s: se potrivește cu un spațiu. Echivalent cu expresia [\t\n\x0B\f\r]
- \S: se potrivește oricărui caracter care nu este un spațiu. Echivalent cu expresia [^\s]
- .: se potrivește oricărui caracter
Este important de menționat că metacaracterul \w se aplică doar literelor din alfabetul latin; literele chirilice nu se potrivesc.
Astfel, pentru a verifica că un cod are doar 4 cifre, am folosit expresia /[0-9][0-9][0-9][0-9]/. O putem simplifica folosind metacaracterul "\d":
const exp = /\d\d\d\d/; // se potrivește cu patru cifre consecutive
const cod1 = "1234";
const cod2 = "jav5";
const cod3 = "3452";
console.log(exp.test(cod1)); // true
console.log(exp.test(cod2)); // false
console.log(exp.test(cod3)); // true
Un alt exemplu. Să presupunem că vrem să găsim șirurile în care este prezent un număr de telefon. Numărul de telefon trebuie să fie în formatul +х-ххх-ххх-хххх:
const exp = /\+\d-\d\d\d-\d\d\d-\d\d\d\d/;
const contact1 = "Email: mycomp@gmail.com";
const contact2 = "Phone: +1-234-567-8901";
console.log(exp.test(contact1)); // false
console.log(exp.test(contact2)); // true
/\+\d-\d\d\d-\d\d\d-\d\d\d\d/ corespunde numărului de telefon +1-234-567-8901.

/\+\d-\d\d\d-\d\d\d-\d\d\d\d/ corespunde numărului de telefon +1-234-567-8901.
Observă bara oblică inversată (\) înainte de semnul plus (+). Deoarece semnul plus (+) are o semnificație specială, pentru a specifica că ne referim la plus ca la un caracter obișnuit al șirului, înaintea lui se adaugă o bară oblică inversată.
Ca rezultat, în șirul "Phone: +1-234-567-8901", metoda exp.test(contact2) va face potrivire cu subșirul "+1-234-567-8901" în raport cu expresia regulată.
Limitarea aplicării expresiilor regulate
O serie de caractere speciale permit limitarea domeniului de aplicare al expresiilor regulate:
- ^: se potrivește începutului șirului. De exemplu, ^h se potrivește șirului "home", dar nu și "ohma", deoarece h trebuie să reprezinte începutul șirului
- $: se potrivește sfârșitului șirului. De exemplu, m$ se potrivește șirului "home", deoarece șirul trebuie să se termine cu litera м.
- \b: se potrivește începutului sau sfârșitului unui cuvânt.
- \B: nu ia în considerare limitele unui cuvânt.
De exemplu, să presupunem că vrem să găsim șirurile cu numere de telefon:
const exp = /\d\d\d\d\d\d\d\d\d\d/; // se potrivește cu 10 cifre consecutive
const telefon1 = "+12345678901";
const telefon2 = "42345678901";
console.log(exp.test(telefon1)); // true
console.log(exp.test(telefon2)); // true
Șablonului /\d\d\d\d\d\d\d\d\d\d/ i se potrivește atât șirul "+12345678901", cât și șirul "42345678901". Dar să presupunem că vrem să găsim numere de telefon care nu încep cu plusul (+). În acest caz, putem folosi expresia regulată /^\d\d\d\d\d\d\d\d\d\d/. Astfel, șirul se va potrivi șablonului doar dacă începe cu caractere numerice:
const exp = /^\d\d\d\d\d\d\d\d\d\d/; // se potrivește cu 10 cifre consecutive
const telefon1 = "+12345678901";
const telefon2 = "42345678901";
console.log(exp.test(telefon1)); // false
console.log(exp.test(telefon2)); // true
Un alt exemplu. Să presupunem că dorim să verificăm dacă într-un șir există menționarea limbajului "Java". Abordarea naivă ar fi să folosim expresia regulată /Java/:
const exp = /Java/;
const str1 = "Java is a high-level, object-oriented programming language";
const str2 = "JavaScript is a programming language of the World Wide Web";
console.log(exp.test(str1)); // true
console.log(exp.test(str2)); // true
Cu toate acestea, în realitate, șablonul "/Java/" se potrivește oricărui șir care conține subșirul "Java", inclusiv șirul "JavaScript". Totuși, dorim să găsim doar acele șiruri în care se vorbește despre Java și nu despre JavaScript. În acest caz, putem limita căutarea cu ajutorul marginilor cuvântului folosind "\b":
const exp = /Java\b/; //
const str1 = "Java is a high-level, object-oriented programming language";
const str2 = "JavaScript is a programming language of the World Wide Web";
console.log(exp.test(str1)); // true
console.log(exp.test(str2)); // false
Flagul "\B", dimpotrivă, indică faptul că șablonul trebuie să se potrivească cu subșiruri care nu sunt cuvinte:
const exp = /Java\B/; //
const str1 = "Java is a high-level, object-oriented programming language";
const str2 = "JavaScript is a programming language of the World Wide Web";
console.log(exp.test(str1)); // false
console.log(exp.test(str2)); // true
Flagurile expresiilor regulate
Flagurile permit ajustarea comportamentului expresiilor regulate. Fiecare flag reprezintă un caracter distinct și se adaugă la sfârșitul expresiei regulate. În JavaScript sunt folosite următoarele flaguri:
- Flagul global (g) permite găsirea tuturor subșirurilor care se potrivesc expresiei regulate. În mod implicit, la căutarea subșirurilor, expresia regulată selectează primul subșir din șir care se potrivește cu expresia. Cu toate acestea, în șir pot exista mai multe subșiruri care se potrivesc cu expresia. Acest flag (`g`) remediază această situație.
- Flagul ignoreCase (i) permite găsirea subșirurilor care se potrivesc expresiei regulate, ignorând cazul literelor din șir. Acesta poate fi utilizat pentru a face ca expresia regulată să fie nereceptor la diferențele de majuscule și minuscule.
- Flagul multiline (m) permite găsirea subșirurilor care se potrivesc expresiei regulate într-un text cu mai multe linii. Acesta poate fi util atunci când căutăm corespondențe care se întind pe mai multe linii.
- Flagul dotAll (s) permite potrivirea punctului în expresia regulată cu orice caracter din text, inclusiv cu separatorul de linie. Acesta schimbă comportamentul implicit al punctului, care nu se potrivește cu separatorul de linie.
De exemplu, flagul `i` se referă la ignorarea diferențelor de caz ale literelor în expresiile regulate.
Să luăm în considerare următorul exemplu:
const str = "Hello World";
const exp = /world/;
console.log(exp.test(str)); // false
Aici nu există o potrivire a șirului cu expresia regulată, deoarece "World" diferă de "world" în ceea ce privește sensibilitatea la majuscule și minuscule. În acest caz, trebuie să modificăm expresia regulată adăugând flag-ul `i`:
const str = "Hello World";
const exp = /world/i;
console.log(exp.test(str)); // true
Observă unde este specificat flag-ul în expresia regulată: /world/i - la sfârșitul expresiei regulate.
Flag-ul s
Flag-ul `s` permite potrivirea caracterului . (punct) cu orice caracter, inclusiv cu separatorul de linie. De exemplu, luăm următorul exemplu:
const str = "hello\nworld";
const exp = /hello world/;
console.log(exp.test(str)); // false
Aici, în șirul "hello\nworld", cuvintele "hello" și "world" sunt separate prin caractere de nouă linie (de exemplu, avem de-a face cu un text pe mai multe linii). Cu toate acestea, să presupunem că dorim ca JavaScript să nu ia în considerare caracterul de nouă linie și să facă ca acest text să se potrivească expresiei regulate /hello world/. În acest caz, putem aplica flag-ul `s`:
const str = "hello\nworld";
const exp = /hello.world/s;
console.log(exp.test(str)); // true
În expresia regulată /hello.world/s, punctul reprezintă orice caracter. Cu toate acestea, fără flag-ul `s`, această expresie nu ar corespunde textului pe mai multe linii.
Combinarea de flag-uri
De asemenea, putem folosi mai multe flag-uri simultan:
const str = "hello\nWorld";
const exp = /hello.world/si;
console.log(exp.test(str)); // true