Reguliere Expressies in JavaScript
Een reguliere expressie (vaak afgekort als regex) is een rij karakters (string) die een tekst
beschrijft. Een goed voorbeeld is het gebruik van wildcards bij het zoeken naar files in MS-DOS
of MS-Windows. Als je alle files zoekt met de extensie .txt gebruik je als zoekpatroon: *.txt
Eigenlijk is dit een heel eenvoudige reguliere expressie. De "echte" regex luidt: .*\.txt
Maar er is veel meer dat je met reguliere expressies kunt doen, zoals checken of een e-mail adres of
postcode correct is gevormd.
Deze pagina geeft slechts een zeer beknopt overzicht van de mogelijkheden. Het is niet bedoeld als tutorial
om het gebruik van reguliere expressies aan te leren.
Voor het aanleren van reguliere expressies bestaat maar één methode:
Volg een tutorial (bijvoorbeeld bij Regular-Expressions.info), leer de syntax uit je hoofd en gebruik het minstens driemaal daags. Anders kun je er maar beter niet aan beginnen...
Het concept van de reguliere expressie is voor het eerst gebruikt in UNIX, bij het doorzoeken en editen
van (tekst-)bestanden. De editors ed en vi gebruiken reguliere expressies om wijzigingen mee
door te voeren.
In programmeertalen zoals Delphi, C++, Perl, Java, PHP, enz. zijn functies en routines beschikbaar voor het
gebruik van reguliere expressies. Hiermee is het mogelijk om in bestanden te zoeken, te wijzigen, enz.
JavaScript is vanaf versie 1.2 standaard voorzien van een object voor het werken met reguliere expressies.
Dat object heet RegExp.
Javascript bevat een volledige implementatie van reguliere expressies. De toepassingen beperken zich
echter voornamelijk tot het testen van invoer in formulieren.
Op deze bladzijde staat beschreven hoe je dit kunt gebruiken. De volgende onderwerpen komen hierbij aan de orde:
- De syntax van reguliere expressies
- Het gebruik van reguliere expressies
- Het JavaScript object RegExp
De hier beschreven informatie is een vrije bewerking van de (engelstalige) website Regular-Expressions.info. Hier is ook een zeer uitgebreide tutorial te vinden. Deze bladzijde beperkt zich tot het beschrijven van de JavaScript-uitvoering van reguliere expressies en het geven van wat voorbeelden.
- Een regex op zich is gewoon een serie karakters, die zelf niets doet. Om de regex wat te laten doen moet er een stukje software (dat de regex-engine (motor) wordt genoemd) worden uitgevoerd. De tekst wordt doorzocht vanaf het begin totdat een stuk tekst is gevonden dat voldoet aan de beschrijving van het patroon in de regex, of tot de tekst op is.
- Zodra er één match is gevonden wordt de zoekactie gestaakt, tenzij je aangeeft dat alle
matches in de string moeten worden behandeld.
Als er een overeenkomst is gevonden wordt dat pattern match genoemd.
De syntax van reguliere expressies
- De syntax (taalbeschijving) van reguliere expressies is: /regexp/modifiers
- De reguliere expressie staat tussen slashes (schuine streepjes). De modifiers ("aanpassers")
zijn optioneel; je kunt ze toepassen als dat handig is.
- De volgende modifiers zijn mogelijk:
- g 'Global matching'. Dit kun je gebruiken om met replace() alle matches in een string te veranderen, in plaats van alleen de eerste.
- i 'case Insensitive'. Er wordt geen onderscheid gemaakt tussen hoofd- en kleine letters.
- s 'Single Line Mode'. Een punt betekent nieuwe regel.
- m 'Multi Line Mode'. Een caret (^ dakje) betekent match aan het begin van de string. Een dollar ( $ ) betekent match aan het einde van de string. Een punt staat voor een willekeurig karaker.
- De syntax van reguliere expressies is nogal uitgebreid. Dat betekent dat je er veel mee kunt doen, maar ook
dat het in elkaar zetten van een correcte reguliere expressie behoorlijk lastig kan zijn als je er weinig
ervaring mee hebt. Een link naar de complete synstaxbeschrijving vind je onderaan deze lijst.
- De syntax kent een aantal begrippen die hier kort de revue passeren:
- Metakarakter
Om onderscheid te kunnen maken tussen de besturing van de regex en de tekst waar naar wordt gekeken, kent de syntax van reguliere expressies een aantal speciale karakters:[\^$.|?*+()
. De regex-motor beschouwt deze karakers als besturingsinformatie. Als je ze wilt gebruiken om te matchen moet je er een backslash\
voor zetten.
Andersom geldt ook: Als je een "gewoon" karakter nodig hebt als besturing van de regex, moet je er vaak ook een backslash voor zetten.
De backslash is het "escape-karakter", dat in JavaScript (en veel andere programmeertalen) ook wordt gebruikt bij het werken met strings. Zie het ook item "Werken met strings". Alle escape codes die bij het werken met strings gebruikt kunnen worden, komen ook voor bij reguliere expressies. - Karakterklasse
Dit is een serie karakters (letters, cijfers, leestekens), waarmee wordt gematcht.
Een karakterklasse staat tussen spekhaken, bijvoorbeeld[A-Za-z0-9\.,]
. Dit zijn alle hoofdletters, kleine letters, cijfers, punt en komma (let op de backslash voor de punt!). - Functie van de punt
De punt kan zowel optreden als "newline"-karakter, of als "elk willeurig karakter". Dit hangt ook af van de modifier die je gebruikt: s of m.
Binnen een karakterklasse verliest een punt echter zijn betekenis en geldt dus gewoon als punt. Het is raadzaam om ook binnen een karakterklasse een backslash voor de punt te zetten. Dat is eenduidiger. - Anker
Hiermee kun je aangeven waar de match moet worden uitgevoerd: Aan het begin van de string, aan het einde van de string, ergens in het midden, enz. De meest gebruikte ankers zijn de caret (^
match aan het begin van de string) en de dollar ($
match aan het einde van de string). Er zijn er
echter nog meer, zie de syntaxbeschijving.
- Metakarakter
- Kwantificeerder
Hiermee geef je aan dat een karakter of karakterpatroon meerdere malen moet voorkomen, bijvoorbeeld 2x. Kwantificeerders staan tussen accolades{ }
. - Alternatief
Hiermee kun je laten kiezen tussen strings. Dit is een logische of, dat wil zeggen: De ene, de andere of allebei. Je geeft het aan met het verticale streepje|
. Dit wordt altijd gebruikt in een groep. - Groepering
Je kunt strings samenvoegen. Dat doe je door ze tussen ronde haakjes( )
te zetten. - Terugverwijzing
Als de regex groepen bevat (dus ronde haakjes) kun je terugverwijzingen gebruiken om tekst te wijzigen.$1
is de eerste terugverwijzing,$2
is de tweede terugverwijzing, enz. Om teksten te wijzigen moet je de replace()-methode van het String-object gebruiken. - Gulzigheid
Kwantificeerders zijn gulzig. Dat betekent dat de regex-motor probeert de match zo groot mogelijk te maken. - Luiheid
Gulzigheid is niet altijd gewenst. Soms wil je het tegenovergestelde. Dan moet je de kwantificeerder lui maken. Dat doe je door een vraagteken?
bij de kwantificeerder op te nemen. De regex-motor zal nu de match zo klein mogelijk maken.
Het gebruik van reguliere expressies
- Om te kijken of een regex matcht met een (deel van ) een string, kun je de String-methode match()
gebruiken, bijvoorbeeld:
if (mijn_String.match(/regex/) {
/*Doe dit als er een match is!*/
} else {
/* Voer anders deze code uit */
}
- Als je de invoer in in formulier-veld wilt testen moet je ankers gebruiken, om zeker te stellen
dat je de hele invoer-string bekijkt en niet alleen een deel. Zie ook bij de voorbeelden onderaan deze
bladzijde.
- Je kunt reguliere expressies gebruiken om strings te veranderen, door een regexp op te geven in
een String-method, bijvoorbeeld: mijn_String.replace(mijn_regexp, "vervangende tekst").
In het laatste voorbeeld hieronder kun je er mee spelen.
- Om een string te splitsen in een array gebruik je de String-methode split(). Bijvoorbeeld:
mijn_array = mijn_String.split(/,/)
Hiermee splits je mijn_String op. Het resultaat is een array. De komma is scheidingsteken in mijn_String. De komma's zelf doen worden uit de array weggelaten.
- Je moet heel vaak gebruik maken van Escape karakters, om te voorkomen dat de reguliere expressie
geheel of gedeeltelijk onjuist wordt geïnterpreteerd.
Zie ook het item "Werken met Strings".
Het JavaScript object RegExp
- Het object RegExp is standaard aanwezig in JavaScript, vanaf versie 1.2. Je hoeft het dus
niet apart te definiëren.
Elk JavaScript proces heeft één eigen RegExp-object, maar je kunt binnen een script net zoveel reguliere expressies aanmaken als je nodig hebt. Hierdoor kunnen vreemde side-effects onstaan, waarover later meer. - De eenvoudigste manier om een reguliere expressie in JavaScript aan te maken is door deze direct als
regex op te geven:
mijn_regexp = /regex/g
Het is natuurlijk wel mogelijk om de regex "formeel" te coderen, maar dat leidt meestal tot moeilijk leesbare code. Zo kun je de regex \w+ opgeven als
re = /\/w+/ (eenvoudig),
maar ook als (moeilijk) re = new RegExp("\\w+")
- Het object RegExp heeft een method genaamd exec(). Dat kun je gebruiken om de
zoekstring in de doorzochte tekst te laten zien, bij voorbeeld:
mijn_match = mijn_regexp.exec("tekst")
Deze function geeft een array terug (hier: mijn_match). Het eerste element (met index 0) bevat de zoektekst. De overige elementen bevatten de overeenkomende tekst tussen de spekhaken (indien aanwezig). De eigenschap mijn_match.index geeft de postitie van de zoekstring aan in de doorzochte tekst. - Aanroep van de exec() function verandert een aantal eigenschappen van het "globale" RegExp object. Dat betekent dat de eigenschappen van alle reguliere expressies binnen het actieve script wijzigen door aanroep van exec().
- Om dit op te vangen kun je gebruik maken van de eigenschappen lastMatch, lastIndex,
leftContext en rightContext.
lastMatch bevat de laatst gevonden string terwijl lastIndex de positie van lastMatch in de doorzochte tekst bevat. Hierbij is terugverwijzing mogelijk.
leftContext en rightContext bevatten de "omgeving" van de gevonden zoekstring. Voorbeeld:
Als er in de string 'keukendeursleutel' is gezocht naar 'deur', is lastMatch = 'deur', lastIndex = 6, leftContext = 'keuken' en rightContext = 'sleutel' .
Voorbeelden
- Test of een invoerveld cijfers bevat:
mijn_string.match(/\d+/) - Test of een invoerveld alléén uit cijfers bestaat:
mijn_string.match(/^\d+$/) - Test of een Nederlandse postcode correct is gevormd (vier cijfers (eerste niet nul), spatie, twee letters (Hoofd-
en kleine letters door elkaar))
mijn_string.match(/^[1-9][0-9]{3}[\s]([A-Z]|[a-z]){2}$/) - Test of een e-mail adres correct is gevormd:
mijn_string.match(/^[\w]{1}[\w\.\-_]*@[\w]{1}[\w\-_\.]*\.[\w]{2,6}$/i)
Zie hiervoor ook het item "Geldigheid testen van een e-mail adres". - Spaties en tabs verwijderen aan het begin en einde van een string:
mijn_string=mijn_string.replace(/(^\s*)|(\s*$)/g, ""); - De juistheid van een IP-adres controleren. Dit ligt niet onmiddellijk voor de hand.
Zie daarvoor het item "Geldigheid testen van een IP-adres". - De juistheid van een datum aanduiding controleren. Ook dit ligt niet onmiddellijk voor de hand.
Zie daarvoor het item "Geldigheid testen van een datum-aanduiding".
- Als je een beetje met reguliere expressies wilt spelen: Klik HIER.