Megosztás a következőn keresztül:


Kvantitátorok reguláris kifejezésekben

A kvantátorok megadják, hogy egy karakter, csoport vagy karakterosztály hány példányának kell szerepelnie a bemenetben ahhoz, hogy egy egyezést találjon. Az alábbi táblázat a .NET által támogatott kvantitátorokat sorolja fel:

Mohó kvantáló Lazy quantifier Leírás
* *? Nulla vagy több alkalommal egyezik.
+ +? Egy vagy több alkalommal egyezik.
? ?? Nullával vagy egyszer egyezik.
{n } {n }? Pontosan n-szer egyezik.
{n ,} {n ,}? Legalább n-szer egyezik.
{n , m } {n , m }? N és m közötti egyezések.

A mennyiségek n és m egész számállandók. A kvantitátorok általában kapzsiak. Ezek hatására a normál kifejezésmotor a lehető legtöbb előfordulásnak felel meg az adott mintákban. Ha hozzáfűzi a ? karaktert egy kvantálóhoz, az lusta lesz. Ez azt eredményezi, hogy a normál kifejezésmotor a lehető legkevesebb előfordulásnak felel meg. A kapzsi és a lusta kvantitátorok közötti különbség teljes leírását a cikk későbbi, Mohó és Lazy Quantifiers című szakaszában találja.

Fontos

A kvantátorok, például a reguláris kifejezésminta (a*)*beágyazása növelheti a reguláris kifejezésmotor által végrehajtandó összehasonlítások számát. Az összehasonlítások száma a bemeneti sztringben szereplő karakterek számának exponenciális függvényeként nőhet. Erről a viselkedésről és a kerülő megoldásokról további információt a Visszakövetés című témakörben talál.

Regular Expression Quantifiers

Az alábbi szakaszok felsorolják a .NET-reguláris kifejezések által támogatott kvantitátorokat:

Feljegyzés

Ha a *, +, ?, {és } karakterek egy reguláris kifejezési mintában jelennek meg, a reguláris kifejezésmotor kvantitátorként vagy kvantitátor-szerkezetek részeként értelmezi őket, kivéve, ha egy karakterosztály tartalmazza őket. Ha ezeket egy karakterosztályon kívüli literális karakterként szeretné értelmezni, el kell őket menekülnie, ha fordított perjellel előzi meg őket. A reguláris kifejezésmintában szereplő sztring \* például literális csillag ("*") karakterként van értelmezve.

Nulla vagy több időpont egyeztetése: *

A * kvantáló megegyezik az előző nullával vagy több alkalommal. Egyenértékű a kvantálóval {0,} . *egy kapzsi kvantáló, amelynek lusta megfelelője .*?

Az alábbi példa ezt a reguláris kifejezést szemlélteti. A bemeneti sztring kilenc számjegycsoportja közül öt egyezik a mintával, és négy (95, 929, 9219és 9919) nem.

string pattern = @"\b91*9*\b";
string input = "99 95 919 929 9119 9219 999 9919 91119";
foreach (Match match in Regex.Matches(input, pattern))
   Console.WriteLine("'{0}' found at position {1}.", match.Value, match.Index);

// The example displays the following output:
//       '99' found at position 0.
//       '919' found at position 6.
//       '9119' found at position 14.
//       '999' found at position 24.
//       '91119' found at position 33.
Dim pattern As String = "\b91*9*\b"
Dim input As String = "99 95 919 929 9119 9219 999 9919 91119"
For Each match As Match In Regex.Matches(input, pattern)
    Console.WriteLine("'{0}' found at position {1}.", match.Value, match.Index)
Next
' The example displays the following output:
'       '99' found at position 0.
'       '919' found at position 6.
'       '9119' found at position 14.
'       '999' found at position 24.
'       '91119' found at position 33.

A reguláris kifejezésminta a következő táblázatban látható módon van definiálva:

Minta Leírás
\b Megadja, hogy az egyezésnek egy szóhatáron kell kezdődnie.
91* Egy nullával 9 vagy több 1 karakterrel egyező karaktert ad meg.
9* Nulla vagy több karakternek felel meg 9 .
\b Megadja, hogy az egyezésnek egy szóhatáron kell végződnie.

Egy vagy több időpont egyeztetése: +

A + kvantáló egy vagy több alkalommal felel meg az előző elemnek. Ez egyenértékű a {1,}. +egy kapzsi kvantáló, amelynek lusta megfelelője .+?

A reguláris kifejezés \ban+\w*?\b például megpróbál egyezni a betűvel kezdődő teljes szavakkal, majd a betű a negy vagy több példányával. Az alábbi példa ezt a reguláris kifejezést szemlélteti. A reguláris kifejezés megegyezik a szavakkal an, annual, announcementés antique, és helyesen nem egyezikautumn.all

string pattern = @"\ban+\w*?\b";

string input = "Autumn is a great time for an annual announcement to all antique collectors.";
foreach (Match match in Regex.Matches(input, pattern, RegexOptions.IgnoreCase))
   Console.WriteLine("'{0}' found at position {1}.", match.Value, match.Index);

// The example displays the following output:
//       'an' found at position 27.
//       'annual' found at position 30.
//       'announcement' found at position 37.
//       'antique' found at position 57.
Dim pattern As String = "\ban+\w*?\b"

Dim input As String = "Autumn is a great time for an annual announcement to all antique collectors."
For Each match As Match In Regex.Matches(input, pattern, RegexOptions.IgnoreCase)
    Console.WriteLine("'{0}' found at position {1}.", match.Value, match.Index)
Next
' The example displays the following output:
'       'an' found at position 27.
'       'annual' found at position 30.
'       'announcement' found at position 37.
'       'antique' found at position 57.

A reguláris kifejezésminta a következő táblázatban látható módon van definiálva:

Minta Leírás
\b Kezdje egy szóhatáron.
an+ a Egy vagy több n karaktert követ.
\w*? Egy szó karakterét nullával vagy többször, de a lehető legkevesebb alkalommal egyezik meg.
\b Egy szóhatáron végződik.

Nulla vagy egyszeri egyezés: ?

A ? kvantáló megegyezik az előző nullával vagy egyszer. Ez egyenértékű a {0,1}. ?egy kapzsi kvantáló, amelynek lusta megfelelője .??

A reguláris kifejezés \ban?\b például a betűvel kezdődő teljes szavakat próbálja egyezni, majd a betű a nnulla vagy egy példányát. Más szóval, megpróbálja egyezni a szavakat a és an. Az alábbi példa ezt a reguláris kifejezést szemlélteti:

string pattern = @"\ban?\b";
string input = "An amiable animal with a large snout and an animated nose.";
foreach (Match match in Regex.Matches(input, pattern, RegexOptions.IgnoreCase))
   Console.WriteLine("'{0}' found at position {1}.", match.Value, match.Index);

// The example displays the following output:
//        'An' found at position 0.
//        'a' found at position 23.
//        'an' found at position 42.
Dim pattern As String = "\ban?\b"
Dim input As String = "An amiable animal with a large snout and an animated nose."
For Each match As Match In Regex.Matches(input, pattern, RegexOptions.IgnoreCase)
    Console.WriteLine("'{0}' found at position {1}.", match.Value, match.Index)
Next
' The example displays the following output:
'       'An' found at position 0.
'       'a' found at position 23.
'       'an' found at position 42.

A reguláris kifejezésminta a következő táblázatban látható módon van definiálva:

Minta Leírás
\b Kezdje egy szóhatáron.
an? a Egy nullával vagy egy n karaktersel egyező karaktert ad meg.
\b Egy szóhatáron végződik.

Pontosan n időpont egyeztetése: {n}

Az {n} kvantáló pontosan n-szer egyezik meg az előző elemmel, ahol n minden egész szám. {n egy kapzsi kvantáló, amelynek lusta megfelelője n}?{.}

A reguláris kifejezés \b\d+\,\d{3}\b például egy szóhatárnak próbál megfelelni, amelyet egy vagy több tizedesjegy követ, majd három tizedesjegy, majd egy szóhatár. Az alábbi példa ezt a reguláris kifejezést szemlélteti:

string pattern = @"\b\d+\,\d{3}\b";
string input = "Sales totaled 103,524 million in January, " +
                      "106,971 million in February, but only " +
                      "943 million in March.";
foreach (Match match in Regex.Matches(input, pattern))
   Console.WriteLine("'{0}' found at position {1}.", match.Value, match.Index);

//  The example displays the following output:
//        '103,524' found at position 14.
//        '106,971' found at position 45.
Dim pattern As String = "\b\d+\,\d{3}\b"
Dim input As String = "Sales totaled 103,524 million in January, " + _
                      "106,971 million in February, but only " + _
                      "943 million in March."
For Each match As Match In Regex.Matches(input, pattern)
    Console.WriteLine("'{0}' found at position {1}.", match.Value, match.Index)
Next
' The example displays the following output:
'       '103,524' found at position 14.
'       '106,971' found at position 45.

A reguláris kifejezésminta a következő táblázatban látható módon van definiálva:

Minta Leírás
\b Kezdje egy szóhatáron.
\d+ Egy vagy több tizedesjegynek felel meg.
\, Egyezik egy vesszővel.
\d{3} Három tizedesjegynek felel meg.
\b Egy szóhatáron végződik.

Legalább n időpont egyeztetése: {n,}

Az {n,} kvantáló legalább n-szer megegyezik az előző elemet, ahol n minden egész szám. {n egy kapzsi kvantáló, amelynek lusta megfelelője n,}?{.,}

A reguláris kifejezés \b\d{2,}\b\D+ például egy szóhatárnak próbál megfelelni, amelyet legalább két számjegy követ, amelyet egy szóhatár és egy nem számjegy karakter követ. Az alábbi példa ezt a reguláris kifejezést szemlélteti. A reguláris kifejezés nem egyezik meg a kifejezéssel "7 days" , mert csak egy tizedesjegyet tartalmaz, de sikeresen megegyezik a kifejezésekkel "10 weeks" és "300 years"a .

string pattern = @"\b\d{2,}\b\D+";
string input = "7 days, 10 weeks, 300 years";
foreach (Match match in Regex.Matches(input, pattern))
   Console.WriteLine("'{0}' found at position {1}.", match.Value, match.Index);

//  The example displays the following output:
//        '10 weeks, ' found at position 8.
//        '300 years' found at position 18.
Dim pattern As String = "\b\d{2,}\b\D+"
Dim input As String = "7 days, 10 weeks, 300 years"
For Each match As Match In Regex.Matches(input, pattern)
    Console.WriteLine("'{0}' found at position {1}.", match.Value, match.Index)
Next
' The example displays the following output:
'       '10 weeks, ' found at position 8.
'       '300 years' found at position 18.

A reguláris kifejezésminta a következő táblázatban látható módon van definiálva:

Minta Leírás
\b Kezdje egy szóhatáron.
\d{2,} Legalább két tizedesjegynek felel meg.
\b Egy szóhatárnak felel meg.
\D+ Legalább egy nem tizedesjegynek felel meg.

Egyezés n és m között: {n,m}

Az {n,m} kvantáló legalább n-szer egyezik meg az előző elemmel, de legfeljebb m alkalommal, ahol az n és az m egész szám. {n,m} egy kapzsi kvantáló, amelynek lusta megfelelője n,{ m.}?

Az alábbi példában a reguláris kifejezés (00\s){2,4} két és négy előfordulás között próbál megegyezni két nulla számjegy és egy szóköz között. A bemeneti sztring utolsó része a legfeljebb négy helyett ötször tartalmazza ezt a mintát. Ennek a részszűrésnek azonban csak a kezdeti része (a szóközig és az ötödik nulla párig) egyezik meg a reguláris kifejezésmintával.

string pattern = @"(00\s){2,4}";
string input = "0x00 FF 00 00 18 17 FF 00 00 00 21 00 00 00 00 00";
foreach (Match match in Regex.Matches(input, pattern))
   Console.WriteLine("'{0}' found at position {1}.", match.Value, match.Index);

//  The example displays the following output:
//        '00 00 ' found at position 8.
//        '00 00 00 ' found at position 23.
//        '00 00 00 00 ' found at position 35.
Dim pattern As String = "(00\s){2,4}"
Dim input As String = "0x00 FF 00 00 18 17 FF 00 00 00 21 00 00 00 00 00"
For Each match As Match In Regex.Matches(input, pattern)
    Console.WriteLine("'{0}' found at position {1}.", match.Value, match.Index)
Next
' The example displays the following output:
'       '00 00 ' found at position 8.
'       '00 00 00 ' found at position 23.
'       '00 00 00 00 ' found at position 35.

Nulla vagy több időpont egyeztetése (lusta egyezés): *?

A *? kvantáló a nulla vagy több alkalommal, de a lehető legkevesebb alkalommal felel meg az előző elemnek. Ez a mohó kvantáló *lusta megfelelője .

Az alábbi példában a reguláris kifejezés \b\w*?oo\w*?\b megegyezik a sztringet ootartalmazó összes szóval.

 string pattern = @"\b\w*?oo\w*?\b";
 string input = "woof root root rob oof woo woe";
 foreach (Match match in Regex.Matches(input, pattern, RegexOptions.IgnoreCase))
    Console.WriteLine("'{0}' found at position {1}.", match.Value, match.Index);

 //  The example displays the following output:
//        'woof' found at position 0.
//        'root' found at position 5.
//        'root' found at position 10.
//        'oof' found at position 19.
//        'woo' found at position 23.
Dim pattern As String = "\b\w*?oo\w*?\b"
Dim input As String = "woof root root rob oof woo woe"
For Each match As Match In Regex.Matches(input, pattern, RegexOptions.IgnoreCase)
    Console.WriteLine("'{0}' found at position {1}.", match.Value, match.Index)
Next
' The example displays the following output:
'       'woof' found at position 0.
'       'root' found at position 5.
'       'root' found at position 10.
'       'oof' found at position 19.
'       'woo' found at position 23.

A reguláris kifejezésminta a következő táblázatban látható módon van definiálva:

Minta Leírás
\b Kezdje egy szóhatáron.
\w*? Nulla vagy több szó karaktert tartalmaz, de a lehető legkevesebb karaktert.
oo Megegyezik a sztringgel oo.
\w*? Nulla vagy több szó karaktert tartalmaz, de a lehető legkevesebb karaktert.
\b Egy szóhatáron végződik.

Egy vagy több időpont egyeztetése (lusta egyezés): +?

A +? kvantáló egy vagy több alkalommal, de a lehető legkevesebb alkalommal felel meg az előző elemnek. Ez a mohó kvantáló +lusta megfelelője .

A reguláris kifejezés \b\w+?\b például egy vagy több, szóhatárok szerint elválasztott karakternek felel meg. Az alábbi példa ezt a reguláris kifejezést szemlélteti:

string pattern = @"\b\w+?\b";
string input = "Aa Bb Cc Dd Ee Ff";
foreach (Match match in Regex.Matches(input, pattern))
   Console.WriteLine("'{0}' found at position {1}.", match.Value, match.Index);

//  The example displays the following output:
//        'Aa' found at position 0.
//        'Bb' found at position 3.
//        'Cc' found at position 6.
//        'Dd' found at position 9.
//        'Ee' found at position 12.
//        'Ff' found at position 15.
Dim pattern As String = "\b\w+?\b"
Dim input As String = "Aa Bb Cc Dd Ee Ff"
For Each match As Match In Regex.Matches(input, pattern)
    Console.WriteLine("'{0}' found at position {1}.", match.Value, match.Index)
Next
' The example displays the following output:
'       'Aa' found at position 0.
'       'Bb' found at position 3.
'       'Cc' found at position 6.
'       'Dd' found at position 9.
'       'Ee' found at position 12.
'       'Ff' found at position 15.

Egyezés nulla vagy egyszer (lazy egyezés): ??

A ?? kvantáló megfelel az előző nulla vagy egy elemnek, de a lehető legkevesebb alkalommal. Ez a mohó kvantáló ?lusta megfelelője .

A reguláris kifejezés ^\s*(System.)??Console.Write(Line)??\(?? például megpróbál megegyezni a sztringekkel Console.Write vagy Console.WriteLinea . A sztring a korábbiakban Consoleis szerepelhetSystem., és egy nyitó zárójel is követhető. A sztringnek egy sor elején kell lennie, bár ezt a szóközzel megelőzheti. Az alábbi példa ezt a reguláris kifejezést szemlélteti:

string pattern = @"^\s*(System.)??Console.Write(Line)??\(??";
string input = "System.Console.WriteLine(\"Hello!\")\n" +
                      "Console.Write(\"Hello!\")\n" +
                      "Console.WriteLine(\"Hello!\")\n" +
                      "Console.ReadLine()\n" +
                      "   Console.WriteLine";
foreach (Match match in Regex.Matches(input, pattern,
                                      RegexOptions.IgnorePatternWhitespace |
                                      RegexOptions.IgnoreCase |
                                      RegexOptions.Multiline))
   Console.WriteLine("'{0}' found at position {1}.", match.Value, match.Index);

//  The example displays the following output:
//        'System.Console.Write' found at position 0.
//        'Console.Write' found at position 36.
//        'Console.Write' found at position 61.
//        '   Console.Write' found at position 110.
Dim pattern As String = "^\s*(System.)??Console.Write(Line)??\(??"
Dim input As String = "System.Console.WriteLine(""Hello!"")" + vbCrLf + _
                      "Console.Write(""Hello!"")" + vbCrLf + _
                      "Console.WriteLine(""Hello!"")" + vbCrLf + _
                      "Console.ReadLine()" + vbCrLf + _
                      "   Console.WriteLine"
For Each match As Match In Regex.Matches(input, pattern, _
                                         RegexOptions.IgnorePatternWhitespace Or RegexOptions.IgnoreCase Or RegexOptions.MultiLine)
    Console.WriteLine("'{0}' found at position {1}.", match.Value, match.Index)
Next
' The example displays the following output:
'       'System.Console.Write' found at position 0.
'       'Console.Write' found at position 36.
'       'Console.Write' found at position 61.
'       '   Console.Write' found at position 110.

A reguláris kifejezésminta a következő táblázatban látható módon van definiálva:

Minta Leírás
^ Megegyezik a bemeneti adatfolyam kezdetével.
\s* Nulla vagy több szóköz karaktert egyezik meg.
(System.)?? Egyezik a sztring System.nullával vagy egy előfordulásával.
Console.Write Megegyezik a sztringgel Console.Write.
(Line)?? Egyezik a sztring Linenullával vagy egy előfordulásával.
\(?? Egyezik a nyitó zárójel nullával vagy egy előfordulásával.

Pontosan n-szer egyezik (lusta egyezés): {n}?

Az {n}? kvantáló pontosan n megfelel az előző elemnek, ahol n az egész szám. Ez a mohó kvantírozó {lusta megfelelője.}

Az alábbi példában a normál kifejezés \b(\w{3,}?\.){2}?\w{3,}?\b egy webhelycím azonosítására szolgál. A kifejezés egyezik www.microsoft.com , de msdn.microsoft.com nem egyezik mywebsite vagy mycompany.com.

string pattern = @"\b(\w{3,}?\.){2}?\w{3,}?\b";
string input = "www.microsoft.com msdn.microsoft.com mywebsite mycompany.com";
foreach (Match match in Regex.Matches(input, pattern))
   Console.WriteLine("'{0}' found at position {1}.", match.Value, match.Index);

//  The example displays the following output:
//        'www.microsoft.com' found at position 0.
//        'msdn.microsoft.com' found at position 18.
Dim pattern As String = "\b(\w{3,}?\.){2}?\w{3,}?\b"
Dim input As String = "www.microsoft.com msdn.microsoft.com mywebsite mycompany.com"
For Each match As Match In Regex.Matches(input, pattern)
    Console.WriteLine("'{0}' found at position {1}.", match.Value, match.Index)
Next
' The example displays the following output:
'       'www.microsoft.com' found at position 0.
'       'msdn.microsoft.com' found at position 18.

A reguláris kifejezésminta a következő táblázatban látható módon van definiálva:

Minta Leírás
\b Kezdje egy szóhatáron.
(\w{3,}?\.) Legalább három szókarakterek, de a lehető legkevesebb karakter, majd egy pont vagy pont karakter. Ez a minta az első rögzítési csoport.
(\w{3,}?\.){2}? Az első csoportban kétszer, de a lehető legkevesebb alkalommal egyezik meg a mintával.
\b Egy szóhatáron fejezd be az egyezést.

Legalább n időpont egyeztetése (Lazy Match): {n,}?

Az {n,}? kvantáló legalább n az előző elemnek felel meg, ahol n bármilyen egész szám, de a lehető legkevesebb alkalommal. Ez a mohó kvantírozó {lusta megfelelője.,}

Az ábrát az {előző szakaszban szereplő n}? kvantáló példában találja. A példában szereplő reguláris kifejezés az {n,} kvantátor használatával egy legalább három karakterből álló sztringet, majd egy pontot használ.

Egyezés n és m időpont között (lusta egyezés): {n,m}?

Az {n,m}? kvantáló megfelel az előző elemnek az idő és m az idő közöttn, ahol az n és az m egész szám, de a lehető legkevesebb alkalommal. Ez a mohó kvantáló {n,m} lusta megfelelője.

Az alábbi példában a reguláris kifejezés \b[A-Z](\w*?\s*?){1,10}[.!?] egyezik az 1 és 10 szó közötti mondatokkal. A bemeneti sztringben szereplő összes mondatnak megfelel, kivéve egy 18 szót tartalmazó mondatot.

string pattern = @"\b[A-Z](\w*?\s*?){1,10}[.!?]";
string input = "Hi. I am writing a short note. Its purpose is " +
                      "to test a regular expression that attempts to find " +
                      "sentences with ten or fewer words. Most sentences " +
                      "in this note are short.";
foreach (Match match in Regex.Matches(input, pattern))
   Console.WriteLine("'{0}' found at position {1}.", match.Value, match.Index);

//  The example displays the following output:
//        'Hi.' found at position 0.
//        'I am writing a short note.' found at position 4.
//        'Most sentences in this note are short.' found at position 132.
Dim pattern As String = "\b[A-Z](\w*\s?){1,10}?[.!?]"
Dim input As String = "Hi. I am writing a short note. Its purpose is " + _
                      "to test a regular expression that attempts to find " + _
                      "sentences with ten or fewer words. Most sentences " + _
                      "in this note are short."
For Each match As Match In Regex.Matches(input, pattern)
    Console.WriteLine("'{0}' found at position {1}.", match.Value, match.Index)
Next
' The example displays the following output:
'       'Hi.' found at position 0.
'       'I am writing a short note.' found at position 4.
'       'Most sentences in this note are short.' found at position 132.

A reguláris kifejezésminta a következő táblázatban látható módon van definiálva:

Minta Leírás
\b Kezdje egy szóhatáron.
[A-Z] Egy nagybetűvel egyezik A-tól Z-ig.
(\w*?\s*?) Nulla vagy több szó karaktert, majd egy vagy több szóköz karaktert tartalmaz, de a lehető legkevesebb alkalommal. Ez a minta az első rögzítési csoport.
{1,10} Megegyezik az előző mintával 1 és 10 között.
[.!?] Egyezik az írásjelek .bármelyikével, !vagy ?.

Mohó és lusta kvantitátorok

Egyes kvantátorok két verzióval rendelkeznek:

  • Egy mohó verzió.

    Egy kapzsi kvantáló a lehető legtöbb alkalommal próbál egy elemet egyezni.

  • Nem mohó (vagy lusta) verzió.

    A nem mohó kvantálók a lehető legkevesebb alkalommal próbálnak egy elemet egyezni. A kapzsi kvantálót lusta kvantálóvá alakíthatja egy ?.

Vegyünk egy reguláris kifejezést, amelynek célja az utolsó négy számjegy kinyerése egy számsorozatból, például hitelkártyaszámból. A kapzsi kvantálót használó * reguláris kifejezés verziója az \b.*([0-9]{4})\b. Ha azonban egy sztring két számot tartalmaz, ez a reguláris kifejezés csak a második szám utolsó négy számjegyével egyezik meg, ahogyan az alábbi példa mutatja:

string greedyPattern = @"\b.*([0-9]{4})\b";
string input1 = "1112223333 3992991999";
foreach (Match match in Regex.Matches(input1, greedyPattern))
   Console.WriteLine("Account ending in ******{0}.", match.Groups[1].Value);

// The example displays the following output:
//       Account ending in ******1999.
Dim greedyPattern As String = "\b.*([0-9]{4})\b"
Dim input1 As String = "1112223333 3992991999"
For Each match As Match In Regex.Matches(input1, greedypattern)
    Console.WriteLine("Account ending in ******{0}.", match.Groups(1).Value)
Next
' The example displays the following output:
'       Account ending in ******1999.

A reguláris kifejezés nem egyezik az első számmal, mert a kvantáló a * lehető legtöbb alkalommal megpróbálja egyezni az előző elemet a teljes sztringben, ezért a sztring végén találja meg az egyezést.

Ez a viselkedés nem a kívánt viselkedés. Ehelyett a *? lusta kvantitálóval mindkét számból kinyerheti a számjegyeket, ahogy az alábbi példa is mutatja:

string lazyPattern = @"\b.*?([0-9]{4})\b";
string input2 = "1112223333 3992991999";
foreach (Match match in Regex.Matches(input2, lazyPattern))
   Console.WriteLine("Account ending in ******{0}.", match.Groups[1].Value);

// The example displays the following output:
//       Account ending in ******3333.
//       Account ending in ******1999.
Dim lazyPattern As String = "\b.*?([0-9]{4})\b"
Dim input2 As String = "1112223333 3992991999"
For Each match As Match In Regex.Matches(input2, lazypattern)
    Console.WriteLine("Account ending in ******{0}.", match.Groups(1).Value)
Next
' The example displays the following output:
'       Account ending in ******3333.
'       Account ending in ******1999.

A legtöbb esetben a kapzsi és lusta kvantitátorok reguláris kifejezései ugyanazokat a találatokat adják vissza. A leggyakrabban különböző eredményeket adnak vissza, ha a helyettesítő karakter (.) metakarakterrel használják őket, amely bármilyen karakternek megfelel.

Kvantitátorok és üres egyezések

A kvantátorok *, +és{ az n,m} és a lusta társaik soha nem ismétlődnek üres egyezés után, amikor a rögzítések minimális száma megtalálható. Ez a szabály megakadályozza, hogy a kvantátorok végtelen hurkokat adjanak meg üres alexpressziós egyezéseken, ha a lehetséges csoportrögzítések maximális száma végtelen vagy közel végtelen.

Az alábbi kód például a metódus meghívásának Regex.Match eredményét jeleníti meg a reguláris kifejezésmintával (a?)*, amely nullával vagy egy a karakter nullával vagy több alkalommal egyezik. Az egyetlen rögzítési csoport rögzíti az egyeseket a , de String.Emptynincs második üres egyezés, mert az első üres egyezés miatt a kvantátor leállítja az ismétlést.

using System;
using System.Text.RegularExpressions;

public class Example
{
   public static void Main()
   {
      string pattern = "(a?)*";
      string input = "aaabbb";
      Match match = Regex.Match(input, pattern);
      Console.WriteLine("Match: '{0}' at index {1}",
                        match.Value, match.Index);
      if (match.Groups.Count > 1) {
         GroupCollection groups = match.Groups;
         for (int grpCtr = 1; grpCtr <= groups.Count - 1; grpCtr++) {
            Console.WriteLine("   Group {0}: '{1}' at index {2}",
                              grpCtr,
                              groups[grpCtr].Value,
                              groups[grpCtr].Index);
            int captureCtr = 0;
            foreach (Capture capture in groups[grpCtr].Captures) {
               captureCtr++;
               Console.WriteLine("      Capture {0}: '{1}' at index {2}",
                                 captureCtr, capture.Value, capture.Index);
            }
         }
      }
   }
}
// The example displays the following output:
//       Match: 'aaa' at index 0
//          Group 1: '' at index 3
//             Capture 1: 'a' at index 0
//             Capture 2: 'a' at index 1
//             Capture 3: 'a' at index 2
//             Capture 4: '' at index 3
Imports System.Text.RegularExpressions

Module Example
    Public Sub Main()
        Dim pattern As String = "(a?)*"
        Dim input As String = "aaabbb"
        Dim match As Match = Regex.Match(input, pattern)
        Console.WriteLine("Match: '{0}' at index {1}",
                          match.Value, match.Index)
        If match.Groups.Count > 1 Then
            Dim groups As GroupCollection = match.Groups
            For grpCtr As Integer = 1 To groups.Count - 1
                Console.WriteLine("   Group {0}: '{1}' at index {2}",
                                  grpCtr,
                                  groups(grpCtr).Value,
                                  groups(grpCtr).Index)
                Dim captureCtr As Integer = 0
                For Each capture As Capture In groups(grpCtr).Captures
                    captureCtr += 1
                    Console.WriteLine("      Capture {0}: '{1}' at index {2}",
                                      captureCtr, capture.Value, capture.Index)
                Next
            Next
        End If
    End Sub
End Module
' The example displays the following output:
'       Match: 'aaa' at index 0
'          Group 1: '' at index 3
'             Capture 1: 'a' at index 0
'             Capture 2: 'a' at index 1
'             Capture 3: 'a' at index 2
'             Capture 4: '' at index 3

A minimális és maximális számú rögzítést meghatározó rögzítési csoport és a rögzített számú rögzítést meghatározó rögzítési csoport közötti gyakorlati különbség megtekintéséhez vegye figyelembe a reguláris kifejezésmintákat (a\1|(?(1)\1)){0,2} és (a\1|(?(1)\1)){2}a . Mindkét reguláris kifejezés egyetlen rögzítési csoportból áll, amely a következő táblázatban van definiálva:

Minta Leírás
(a\1 Bármelyik egyezés a az első rögzített csoport értékével együtt ...
|(?(1) … vagy ellenőrzi, hogy az első rögzített csoport definiálva van-e. A (?(1) szerkezet nem definiál rögzítési csoportot.
\1)) Ha az első rögzített csoport létezik, egyezzen az értékével. Ha a csoport nem létezik, a csoport egyezni String.Emptyfog.

Az első reguláris kifejezés nullától kétig próbál megegyezni a mintával; a másodikat, pontosan kétszer. Mivel az első minta eléri a rögzítések minimális számát az első rögzítésével String.Empty, soha nem ismétlődik, hogy megpróbáljon megegyezni a\1. A {0,2} kvantáló csak üres egyezéseket engedélyez az utolsó iterációban. Ezzel szemben a második reguláris kifejezés megegyezik a , mert másodszor is kiértékeli a\1 . Az iterációk minimális száma (2) arra kényszeríti a motort, hogy üres egyezés után ismételjen.

using System;
using System.Text.RegularExpressions;

public class Example
{
   public static void Main()
   {
      string pattern, input;

      pattern = @"(a\1|(?(1)\1)){0,2}";
      input = "aaabbb";

      Console.WriteLine("Regex pattern: {0}", pattern);
      Match match = Regex.Match(input, pattern);
      Console.WriteLine("Match: '{0}' at position {1}.",
                        match.Value, match.Index);
      if (match.Groups.Count > 1) {
         for (int groupCtr = 1; groupCtr <= match.Groups.Count - 1; groupCtr++)
         {
            Group group = match.Groups[groupCtr];
            Console.WriteLine("   Group: {0}: '{1}' at position {2}.",
                              groupCtr, group.Value, group.Index);
            int captureCtr = 0;
            foreach (Capture capture in group.Captures) {
               captureCtr++;
               Console.WriteLine("      Capture: {0}: '{1}' at position {2}.",
                                 captureCtr, capture.Value, capture.Index);
            }
         }
      }
      Console.WriteLine();

      pattern = @"(a\1|(?(1)\1)){2}";
      Console.WriteLine("Regex pattern: {0}", pattern);
      match = Regex.Match(input, pattern);
         Console.WriteLine("Matched '{0}' at position {1}.",
                           match.Value, match.Index);
      if (match.Groups.Count > 1) {
         for (int groupCtr = 1; groupCtr <= match.Groups.Count - 1; groupCtr++)
         {
            Group group = match.Groups[groupCtr];
            Console.WriteLine("   Group: {0}: '{1}' at position {2}.",
                              groupCtr, group.Value, group.Index);
            int captureCtr = 0;
            foreach (Capture capture in group.Captures) {
               captureCtr++;
               Console.WriteLine("      Capture: {0}: '{1}' at position {2}.",
                                 captureCtr, capture.Value, capture.Index);
            }
         }
      }
   }
}
// The example displays the following output:
//       Regex pattern: (a\1|(?(1)\1)){0,2}
//       Match: '' at position 0.
//          Group: 1: '' at position 0.
//             Capture: 1: '' at position 0.
//
//       Regex pattern: (a\1|(?(1)\1)){2}
//       Matched 'a' at position 0.
//          Group: 1: 'a' at position 0.
//             Capture: 1: '' at position 0.
//             Capture: 2: 'a' at position 0.
Imports System.Text.RegularExpressions

Module Example
    Public Sub Main()
        Dim pattern, input As String

        pattern = "(a\1|(?(1)\1)){0,2}"
        input = "aaabbb"

        Console.WriteLine("Regex pattern: {0}", pattern)
        Dim match As Match = Regex.Match(input, pattern)
        Console.WriteLine("Match: '{0}' at position {1}.",
                          match.Value, match.Index)
        If match.Groups.Count > 1 Then
            For groupCtr As Integer = 1 To match.Groups.Count - 1
                Dim group As Group = match.Groups(groupCtr)
                Console.WriteLine("   Group: {0}: '{1}' at position {2}.",
                                  groupCtr, group.Value, group.Index)
                Dim captureCtr As Integer = 0
                For Each capture As Capture In group.Captures
                    captureCtr += 1
                    Console.WriteLine("      Capture: {0}: '{1}' at position {2}.",
                                      captureCtr, capture.Value, capture.Index)
                Next
            Next
        End If
        Console.WriteLine()

        pattern = "(a\1|(?(1)\1)){2}"
        Console.WriteLine("Regex pattern: {0}", pattern)
        match = Regex.Match(input, pattern)
        Console.WriteLine("Matched '{0}' at position {1}.",
                          match.Value, match.Index)
        If match.Groups.Count > 1 Then
            For groupCtr As Integer = 1 To match.Groups.Count - 1
                Dim group As Group = match.Groups(groupCtr)
                Console.WriteLine("   Group: {0}: '{1}' at position {2}.",
                                  groupCtr, group.Value, group.Index)
                Dim captureCtr As Integer = 0
                For Each capture As Capture In group.Captures
                    captureCtr += 1
                    Console.WriteLine("      Capture: {0}: '{1}' at position {2}.",
                                      captureCtr, capture.Value, capture.Index)
                Next
            Next
        End If
    End Sub
End Module
' The example displays the following output:
'       Regex pattern: (a\1|(?(1)\1)){0,2}
'       Match: '' at position 0.
'          Group: 1: '' at position 0.
'             Capture: 1: '' at position 0.
'       
'       Regex pattern: (a\1|(?(1)\1)){2}
'       Matched 'a' at position 0.
'          Group: 1: 'a' at position 0.
'             Capture: 1: '' at position 0.
'             Capture: 2: 'a' at position 0.

Lásd még