Možnosti regulárních výrazů
Ve výchozím nastavení porovnání vstupního řetězce s jakýmkoli literálovým znakem ve vzoru regulárního výrazu rozlišuje velká a malá písmena, prázdné znaky ve vzoru regulárního výrazu jsou interpretovány jako literální prázdné znaky a zachytávající skupiny v regulárním výrazu jsou pojmenovány implicitně a také explicitně. Můžete upravit tyto a několik dalších aspektů výchozího chování regulárních výrazů zadáním možností regulárních výrazů. Tyto možnosti, které jsou uvedeny v následující tabulce, mohou být zahrnuty vložené jako součást vzoru regulárního výrazu, nebo mohou být zadány do System.Text.RegularExpressions.Regex konstruktoru třídy nebo statické metody porovnávání vzorů jako System.Text.RegularExpressions.RegexOptions hodnota výčtu.
| Člen RegexOptions | Vložený znak | Účinek |
|---|---|---|
| None | Není k dispozici | Použijte výchozí chování. Další informace najdete v tématu výchozí možnosti. |
| IgnoreCase | i |
Použije porovnávání, které nerozlišuje velká a malá písmena. Další informace naleznete v tématu porovnávání bez rozlišování velkých amalých písmen. |
| Multiline | m |
Použijte víceřádkový režim, kde ^ a $ odpovídají začátku a konci každého řádku (místo začátku a konce vstupního řetězce). Další informace najdete v tématu víceřádkový režim. |
| Singleline | s |
Použijte jednořádkový režim, kde tečka (.) odpovídá každému znaku (místo každého znaku kromě \n ). Další informace najdete v tématu jednořádkový režim. |
| ExplicitCapture | n |
Nezachytí nepojmenované skupiny. Jedinými platnými zachyceními jsou explicitně pojmenované nebo číslované skupiny dílčího (?< > výrazu názvu formuláře ) . Další informace naleznete v tématu pouze explicitní zachycení. |
| Compiled | Není k dispozici | Zkompilujte regulární výraz do sestavení. Další informace naleznete v tématu kompilované regulární výrazy. |
| IgnorePatternWhitespace | x |
Vylučte prázdné znaky bez řídicích znaků ze vzoru a povolte komentáře za znakem čísla ( # ). Další informace naleznete v tématu Ignorovat prázdnéznaky. |
| RightToLeft | Není k dispozici | Změňte směr hledání. Hledání se přesune zprava doleva, nikoli zleva doprava. Další informace najdete v tématu Režim zprava doleva. |
| ECMAScript | Není k dispozici | Povolí chování standardu ECMAScript pro výraz. Další informace naleznete v tématu chování při shodě ECMAScript. |
| CultureInvariant | Není k dispozici | Ignorujte kulturní rozdíly v jazyce. Další informace naleznete v tématu porovnání s použitím invariantní jazykové verze. |
Zadání možností
Možnosti regulárních výrazů lze zadat jedním ze tří způsobů:
v
optionsparametru System.Text.RegularExpressions.Regex konstruktoru třídy nebo statickéSharedmetody (v Visual Basic) pro porovnávání vzorů, například Regex(String, RegexOptions) nebo Regex.Match(String, String, RegexOptions) .optionsParametr je bitová nebo kombinace System.Text.RegularExpressions.RegexOptions hodnot výčtu.Pokud jsou možnosti poskytnuty Regex instanci pomocí
optionsparametru konstruktoru třídy, jsou možnosti přiřazeny System.Text.RegularExpressions.RegexOptions Vlastnosti. System.Text.RegularExpressions.RegexOptionsVlastnost však neodráží vložené možnosti ve vzorku regulárního výrazu.V následujícím příkladu je uvedena ukázka. Používá
optionsparametr Regex.Match(String, String, RegexOptions) metody pro povolení porovnávání bez rozlišování velkých a malých písmen a při identifikaci slov začínajících písmenem "d" Ignorovat prázdné znaky vzoru.string pattern = @"d \w+ \s"; string input = "Dogs are decidedly good pets."; RegexOptions options = RegexOptions.IgnoreCase | RegexOptions.IgnorePatternWhitespace; foreach (Match match in Regex.Matches(input, pattern, options)) Console.WriteLine("'{0}// found at index {1}.", match.Value, match.Index); // The example displays the following output: // 'Dogs // found at index 0. // 'decidedly // found at index 9.Dim pattern As String = "d \w+ \s" Dim input As String = "Dogs are decidedly good pets." Dim options As RegexOptions = RegexOptions.IgnoreCase Or RegexOptions.IgnorePatternWhitespace For Each match As Match In Regex.Matches(input, pattern, options) Console.WriteLine("'{0}' found at index {1}.", match.Value, match.Index) Next ' The example displays the following output: ' 'Dogs ' found at index 0. ' 'decidedly ' found at index 9.Použitím vložených možností ve vzoru regulárního výrazu se syntaxí
(?imnsx-imnsx). Možnost se vztahuje na vzor z bodu, ve kterém je možnost definována, buď na konec vzoru, nebo na bod, ve kterém není možnost definována jinou vloženou možností. Všimněte si, že System.Text.RegularExpressions.RegexOptions vlastnost Regex instance neodráží tyto vložené možnosti. Další informace naleznete v tématu různé konstruktory .V následujícím příkladu je uvedena ukázka. Používá vložené možnosti pro povolení porovnávání bez rozlišování velkých a malých písmen a při identifikaci slov začínajících písmenem "d" Ignorovat prázdné znaky vzoru.
string pattern = @"(?ix) d \w+ \s"; string input = "Dogs are decidedly good pets."; foreach (Match match in Regex.Matches(input, pattern)) Console.WriteLine("'{0}// found at index {1}.", match.Value, match.Index); // The example displays the following output: // 'Dogs // found at index 0. // 'decidedly // found at index 9.Dim pattern As String = "\b(?ix) d \w+ \s" Dim input As String = "Dogs are decidedly good pets." For Each match As Match In Regex.Matches(input, pattern) Console.WriteLine("'{0}' found at index {1}.", match.Value, match.Index) Next ' The example displays the following output: ' 'Dogs ' found at index 0. ' 'decidedly ' found at index 9.Použitím vložených možností v konkrétní seskupovací konstrukci ve vzoru regulárního výrazu s
(?imnsx-imnsx:podvýrazem syntaxe). Žádné znaménko před tím, než sada možností zapne. znaménko mínus před sadou možností je vypnuto. (?je pevně daná část syntaxe konstrukce jazyka, která je vyžadována, pokud jsou možnosti povoleny nebo zakázány.) Možnost se vztahuje pouze na tuto skupinu. Další informace naleznete v tématu seskupovací konstrukce.V následujícím příkladu je uvedena ukázka. Používá vložené možnosti v seskupovací konstrukci pro povolení porovnávání bez rozlišování velkých a malých písmen a při identifikaci slov, která začínají písmenem "d", ignoruje vzory prázdné znaky.
string pattern = @"\b(?ix: d \w+)\s"; string input = "Dogs are decidedly good pets."; foreach (Match match in Regex.Matches(input, pattern)) Console.WriteLine("'{0}// found at index {1}.", match.Value, match.Index); // The example displays the following output: // 'Dogs // found at index 0. // 'decidedly // found at index 9.Dim pattern As String = "\b(?ix: d \w+)\s" Dim input As String = "Dogs are decidedly good pets." For Each match As Match In Regex.Matches(input, pattern) Console.WriteLine("'{0}' found at index {1}.", match.Value, match.Index) Next ' The example displays the following output: ' 'Dogs ' found at index 0. ' 'decidedly ' found at index 9.
Pokud jsou možnosti zadány jako vložené, znaménko mínus ( - ) před možností nebo sadou možností vypne tyto možnosti. Například vložená konstrukce (?ix-ms) zapne RegexOptions.IgnoreCase a RegexOptions.IgnorePatternWhitespace Možnosti a vypne RegexOptions.Multiline RegexOptions.Singleline Možnosti a. Ve výchozím nastavení jsou všechny možnosti regulárních výrazů vypnuté.
Poznámka
Pokud jsou možnosti regulárních výrazů zadané v options parametru konstruktoru nebo volání metody v konfliktu s možnostmi určenými jako vložené ve vzoru regulárního výrazu, jsou použity vložené možnosti.
Následující pět možností regulárních výrazů lze nastavit pomocí parametru options i inline:
Následující pět možností regulárních výrazů lze nastavit pomocí parametru, options ale nelze je nastavit jako vložené:
Určení možností
Můžete určit, které možnosti byly poskytnuty Regex objektu při vytvoření instance načtením hodnoty vlastnosti jen pro čtení Regex.Options . Tato vlastnost je zvláště užitečná pro určení možností, které jsou definovány pro zkompilovaný regulární výraz vytvořený Regex.CompileToAssembly metodou.
Chcete-li otestovat přítomnost jakékoli možnosti s výjimkou RegexOptions.None , proveďte operaci a s hodnotou Regex.Options vlastnosti a hodnotou, se kterou RegexOptions vás zajímáte. Pak testujte, jestli výsledek odpovídá RegexOptions hodnotě. Následující příklad testuje, zda byla RegexOptions.IgnoreCase možnost nastavena.
if ((rgx.Options & RegexOptions.IgnoreCase) == RegexOptions.IgnoreCase)
Console.WriteLine("Case-insensitive pattern comparison.");
else
Console.WriteLine("Case-sensitive pattern comparison.");
If (rgx.Options And RegexOptions.IgnoreCase) = RegexOptions.IgnoreCase Then
Console.WriteLine("Case-insensitive pattern comparison.")
Else
Console.WriteLine("Case-sensitive pattern comparison.")
End If
Chcete-li otestovat RegexOptions.None , určete, zda je hodnota Regex.Options vlastnosti rovna RegexOptions.None , jak ukazuje následující příklad.
if (rgx.Options == RegexOptions.None)
Console.WriteLine("No options have been set.");
If rgx.Options = RegexOptions.None Then
Console.WriteLine("No options have been set.")
End If
V následujících částech jsou uvedeny možnosti podporované regulárním výrazem v rozhraní .NET.
Výchozí možnosti
RegexOptions.NoneMožnost označuje, že nebyly zadány žádné možnosti, a modul regulárních výrazů používá jeho výchozí chování. Ta zahrnují následující:
Vzor je interpretován jako kanonický namísto regulárního výrazu ECMAScript.
Vzor regulárního výrazu je porovnán ve vstupním řetězci zleva doprava.
Při porovnávání se rozlišují malá a velká písmena.
^$Prvky jazyka a odpovídají začátku a konci vstupního řetězce. Konec vstupního řetězce může být koncovým\nznakem nového řádku..Prvek jazyka odpovídá každému znaku s výjimkou\n.Jakékoli prázdné místo ve vzoru regulárního výrazu je interpretováno jako literální znak mezery.
Konvence aktuální jazykové verze se používají při porovnávání vzoru se vstupním řetězcem.
Zachytávající skupiny ve vzoru regulárního výrazu jsou implicitní a také explicitní.
Poznámka
RegexOptions.NoneMožnost nemá žádný vložený ekvivalent. Pokud jsou možnosti regulárních výrazů aplikovány na hodnotu inline, je výchozí chování obnoveno na základě možností podle možnosti vypnutím konkrétní možnosti. Například (?i) zapíná porovnávání bez rozlišení velkých a malých písmen a (?-i) obnoví výchozí porovnání rozlišující velká a malá písmena.
Vzhledem k tomu, že RegexOptions.None možnost představuje výchozí chování modulu regulárních výrazů, je zřídka explicitně určena ve volání metody. Místo toho se volá konstruktor nebo statická metoda porovnávání vzorů bez options parametru.
Case-Insensitive – shoda
IgnoreCaseMožnost nebo i vložená možnost poskytuje porovnávání bez rozlišení velkých a malých písmen. Ve výchozím nastavení se používají konvence pro velká a malá písmena aktuální jazykové verze.
Následující příklad definuje vzor regulárního výrazu, \bthe\w*\b který odpovídá všem slovům začínajícím na "The". Vzhledem k tomu, že první volání Match metody používá výchozí porovnání rozlišující velká a malá písmena, výstup označuje, že řetězec "The", který začíná větu, se neshoduje. Je porovnána, pokud Match je metoda volána s možnostmi nastavenými na IgnoreCase .
using System;
using System.Text.RegularExpressions;
public class Example
{
public static void Main()
{
string pattern = @"\bthe\w*\b";
string input = "The man then told them about that event.";
foreach (Match match in Regex.Matches(input, pattern))
Console.WriteLine("Found {0} at index {1}.", match.Value, match.Index);
Console.WriteLine();
foreach (Match match in Regex.Matches(input, pattern,
RegexOptions.IgnoreCase))
Console.WriteLine("Found {0} at index {1}.", match.Value, match.Index);
}
}
// The example displays the following output:
// Found then at index 8.
// Found them at index 18.
//
// Found The at index 0.
// Found then at index 8.
// Found them at index 18.
Imports System.Text.RegularExpressions
Module Example
Public Sub Main()
Dim pattern As String = "\bthe\w*\b"
Dim input As String = "The man then told them about that event."
For Each match As Match In Regex.Matches(input, pattern)
Console.WriteLine("Found {0} at index {1}.", match.Value, match.Index)
Next
Console.WriteLine()
For Each match As Match In Regex.Matches(input, pattern, _
RegexOptions.IgnoreCase)
Console.WriteLine("Found {0} at index {1}.", match.Value, match.Index)
Next
End Sub
End Module
' The example displays the following output:
' Found then at index 8.
' Found them at index 18.
'
' Found The at index 0.
' Found then at index 8.
' Found them at index 18.
Následující příklad upravuje vzor regulárního výrazu z předchozího příkladu pro použití vložených možností namísto options parametru pro poskytnutí porovnání bez rozlišování velkých a malých písmen. První vzor definuje možnost nerozlišuje velká a malá písmena v seskupovací konstrukci, která se vztahuje pouze na písmeno "t" v řetězci "The". Vzhledem k tomu, že konstrukce možnosti probíhá na začátku vzoru, druhý vzor použije možnost nerozlišuje velká a malá písmena na celý regulární výraz.
using System;
using System.Text.RegularExpressions;
public class Example
{
public static void Main()
{
string pattern = @"\b(?i:t)he\w*\b";
string input = "The man then told them about that event.";
foreach (Match match in Regex.Matches(input, pattern))
Console.WriteLine("Found {0} at index {1}.", match.Value, match.Index);
Console.WriteLine();
pattern = @"(?i)\bthe\w*\b";
foreach (Match match in Regex.Matches(input, pattern,
RegexOptions.IgnoreCase))
Console.WriteLine("Found {0} at index {1}.", match.Value, match.Index);
}
}
// The example displays the following output:
// Found The at index 0.
// Found then at index 8.
// Found them at index 18.
//
// Found The at index 0.
// Found then at index 8.
// Found them at index 18.
Imports System.Text.RegularExpressions
Module Example
Public Sub Main()
Dim pattern As String = "\b(?i:t)he\w*\b"
Dim input As String = "The man then told them about that event."
For Each match As Match In Regex.Matches(input, pattern)
Console.WriteLine("Found {0} at index {1}.", match.Value, match.Index)
Next
Console.WriteLine()
pattern = "(?i)\bthe\w*\b"
For Each match As Match In Regex.Matches(input, pattern)
Console.WriteLine("Found {0} at index {1}.", match.Value, match.Index)
Next
End Sub
End Module
' The example displays the following output:
' Found The at index 0.
' Found then at index 8.
' Found them at index 18.
'
' Found The at index 0.
' Found then at index 8.
' Found them at index 18.
Víceřádkový režim
RegexOptions.MultilineMožnost nebo m vložená možnost umožňuje modulu regulárních výrazů zpracovat vstupní řetězec, který se skládá z více řádků. Změní výklad ^ $ prvků jazyka a tak, aby odpovídaly začátku a konci řádku místo začátku a konce vstupního řetězce.
Ve výchozím nastavení $ odpovídá pouze konci vstupního řetězce. Pokud zadáte RegexOptions.Multiline možnost , bude odpovídat znaku nového řádku ( ) nebo konci \n vstupního řetězce. Neodpovídá ale kombinaci znaku návratu na řádek a znak od znaku. Pokud je chcete úspěšně porovnat, použijte dílčí výraz \r?$ místo pouze $ .
Následující příklad extrahuje názvy a skóre náhazků a přidá je do kolekce, která je seřadí SortedList<TKey,TValue> v sestupném pořadí. Metoda Matches je volána dvakrát. V prvním volání metody je regulární výraz a ^(\w+)\s(\d+)$ nejsou nastaveny žádné možnosti. Jak ukazuje výstup, protože modul regulárních výrazů nemůže odpovídat vstupnímu vzoru spolu se začátkem a koncem vstupního řetězce, nenašly se žádné shody. Ve druhém volání metody se regulární výraz změní na a ^(\w+)\s(\d+)\r?$ možnosti jsou nastaveny na RegexOptions.Multiline . Jak ukazuje výstup, názvy a skóre se úspěšně shodují a skóre se zobrazí v sestupném pořadí.
using System;
using System.Collections.Generic;
using System.Text.RegularExpressions;
public class Example
{
public static void Main()
{
SortedList<int, string> scores = new SortedList<int, string>(new DescendingComparer<int>());
string input = "Joe 164\n" +
"Sam 208\n" +
"Allison 211\n" +
"Gwen 171\n";
string pattern = @"^(\w+)\s(\d+)$";
bool matched = false;
Console.WriteLine("Without Multiline option:");
foreach (Match match in Regex.Matches(input, pattern))
{
scores.Add(Int32.Parse(match.Groups[2].Value), (string) match.Groups[1].Value);
matched = true;
}
if (! matched)
Console.WriteLine(" No matches.");
Console.WriteLine();
// Redefine pattern to handle multiple lines.
pattern = @"^(\w+)\s(\d+)\r*$";
Console.WriteLine("With multiline option:");
foreach (Match match in Regex.Matches(input, pattern, RegexOptions.Multiline))
scores.Add(Int32.Parse(match.Groups[2].Value), (string) match.Groups[1].Value);
// List scores in descending order.
foreach (KeyValuePair<int, string> score in scores)
Console.WriteLine("{0}: {1}", score.Value, score.Key);
}
}
public class DescendingComparer<T> : IComparer<T>
{
public int Compare(T x, T y)
{
return Comparer<T>.Default.Compare(x, y) * -1;
}
}
// The example displays the following output:
// Without Multiline option:
// No matches.
//
// With multiline option:
// Allison: 211
// Sam: 208
// Gwen: 171
// Joe: 164
Imports System.Collections.Generic
Imports System.Text.RegularExpressions
Module Example
Public Sub Main()
Dim scores As New SortedList(Of Integer, String)(New DescendingComparer(Of Integer)())
Dim input As String = "Joe 164" + vbCrLf + _
"Sam 208" + vbCrLf + _
"Allison 211" + vbCrLf + _
"Gwen 171" + vbCrLf
Dim pattern As String = "^(\w+)\s(\d+)$"
Dim matched As Boolean = False
Console.WriteLine("Without Multiline option:")
For Each match As Match In Regex.Matches(input, pattern)
scores.Add(CInt(match.Groups(2).Value), match.Groups(1).Value)
matched = True
Next
If Not matched Then Console.WriteLine(" No matches.")
Console.WriteLine()
' Redefine pattern to handle multiple lines.
pattern = "^(\w+)\s(\d+)\r*$"
Console.WriteLine("With multiline option:")
For Each match As Match In Regex.Matches(input, pattern, RegexOptions.Multiline)
scores.Add(CInt(match.Groups(2).Value), match.Groups(1).Value)
Next
' List scores in descending order.
For Each score As KeyValuePair(Of Integer, String) In scores
Console.WriteLine("{0}: {1}", score.Value, score.Key)
Next
End Sub
End Module
Public Class DescendingComparer(Of T) : Implements IComparer(Of T)
Public Function Compare(x As T, y As T) As Integer _
Implements IComparer(Of T).Compare
Return Comparer(Of T).Default.Compare(x, y) * -1
End Function
End Class
' The example displays the following output:
' Without Multiline option:
' No matches.
'
' With multiline option:
' Allison: 211
' Sam: 208
' Gwen: 171
' Joe: 164
Vzor regulárního ^(\w+)\s(\d+)\r*$ výrazu je definován tak, jak je znázorněno v následující tabulce.
| Vzor | Popis |
|---|---|
^ |
Začněte na začátku řádku. |
(\w+) |
Porovná jeden nebo více znaků slova. Toto je první zachytávající skupina. |
\s |
Porovná prázdný znak. |
(\d+) |
Porovná jednu nebo více desítkových číslic. Toto je druhá zachytávající skupina. |
\r? |
Porovná žádný nebo jeden znak návratu na znak konce řádku. |
$ |
Končí na konci řádku. |
Následující příklad je ekvivalentem předchozího příkladu s tím rozdílem, že k nastavení víceřádkové možnosti používá vložené (?m) možnosti.
using System;
using System.Collections.Generic;
using System.Text.RegularExpressions;
public class Example
{
public static void Main()
{
SortedList<int, string> scores = new SortedList<int, string>(new DescendingComparer<int>());
string input = "Joe 164\n" +
"Sam 208\n" +
"Allison 211\n" +
"Gwen 171\n";
string pattern = @"(?m)^(\w+)\s(\d+)\r*$";
foreach (Match match in Regex.Matches(input, pattern, RegexOptions.Multiline))
scores.Add(Convert.ToInt32(match.Groups[2].Value), match.Groups[1].Value);
// List scores in descending order.
foreach (KeyValuePair<int, string> score in scores)
Console.WriteLine("{0}: {1}", score.Value, score.Key);
}
}
public class DescendingComparer<T> : IComparer<T>
{
public int Compare(T x, T y)
{
return Comparer<T>.Default.Compare(x, y) * -1;
}
}
// The example displays the following output:
// Allison: 211
// Sam: 208
// Gwen: 171
// Joe: 164
Imports System.Collections.Generic
Imports System.Text.RegularExpressions
Module Example
Public Sub Main()
Dim scores As New SortedList(Of Integer, String)(New DescendingComparer(Of Integer)())
Dim input As String = "Joe 164" + vbCrLf + _
"Sam 208" + vbCrLf + _
"Allison 211" + vbCrLf + _
"Gwen 171" + vbCrLf
Dim pattern As String = "(?m)^(\w+)\s(\d+)\r*$"
For Each match As Match In Regex.Matches(input, pattern, RegexOptions.Multiline)
scores.Add(CInt(match.Groups(2).Value), match.Groups(1).Value)
Next
' List scores in descending order.
For Each score As KeyValuePair(Of Integer, String) In scores
Console.WriteLine("{0}: {1}", score.Value, score.Key)
Next
End Sub
End Module
Public Class DescendingComparer(Of T) : Implements IComparer(Of T)
Public Function Compare(x As T, y As T) As Integer _
Implements IComparer(Of T).Compare
Return Comparer(Of T).Default.Compare(x, y) * -1
End Function
End Class
' The example displays the following output:
' Allison: 211
' Sam: 208
' Gwen: 171
' Joe: 164
Jedno řádkové režimy
Možnost RegexOptions.Singleline nebo možnost inline způsobí, že modul regulárních výrazů bude se vstupním řetězcem zacházet, jako by se sčítá s z jednoho řádku. Dělá to tak, že změní chování elementu jazyka tečky ( ) tak, aby odpovídaly každému znaku místo porovnávání každého znaku s výjimkou znaku nového řádku . \n nebo \u000A .
Prvek $ jazyka bude odpovídat konci řetězce nebo koncovému znaku nového řádku \n .
Následující příklad ukazuje, jak se změní chování . elementu jazyka při použití RegexOptions.Singleline možnosti . Regulární výraz začíná na začátku řetězce a ^.+ odpovídá každému znaku. Ve výchozím nastavení končí shoda na konci prvního řádku. Vzor regulárního výrazu odpovídá znaku návratu na řádku \r nebo \u000D, ale neodpovídá \n znaku . Vzhledem k tomu, že možnost interpretuje celý vstupní řetězec jako jeden řádek, odpovídá každému znaku ve RegexOptions.Singleline vstupním řetězci, včetně \n .
using System;
using System.Text.RegularExpressions;
public class Example
{
public static void Main()
{
string pattern = "^.+";
string input = "This is one line and" + Environment.NewLine + "this is the second.";
foreach (Match match in Regex.Matches(input, pattern))
Console.WriteLine(Regex.Escape(match.Value));
Console.WriteLine();
foreach (Match match in Regex.Matches(input, pattern, RegexOptions.Singleline))
Console.WriteLine(Regex.Escape(match.Value));
}
}
// The example displays the following output:
// This\ is\ one\ line\ and\r
//
// This\ is\ one\ line\ and\r\nthis\ is\ the\ second\.
Imports System.Text.RegularExpressions
Module Example
Public Sub Main()
Dim pattern As String = "^.+"
Dim input As String = "This is one line and" + vbCrLf + "this is the second."
For Each match As Match In Regex.Matches(input, pattern)
Console.WriteLine(Regex.Escape(match.Value))
Next
Console.WriteLine()
For Each match As Match In Regex.Matches(input, pattern, RegexOptions.SingleLine)
Console.WriteLine(Regex.Escape(match.Value))
Next
End Sub
End Module
' The example displays the following output:
' This\ is\ one\ line\ and\r
'
' This\ is\ one\ line\ and\r\nthis\ is\ the\ second\.
Následující příklad je ekvivalentní předchozímu příkladu s tím rozdílem, že k povolení jednořádkového režimu používá vložené (?s) možnosti.
using System;
using System.Text.RegularExpressions;
public class Example
{
public static void Main()
{
string pattern = "(?s)^.+";
string input = "This is one line and" + Environment.NewLine + "this is the second.";
foreach (Match match in Regex.Matches(input, pattern))
Console.WriteLine(Regex.Escape(match.Value));
}
}
// The example displays the following output:
// This\ is\ one\ line\ and\r\nthis\ is\ the\ second\.
Imports System.Text.RegularExpressions
Module Example
Public Sub Main()
Dim pattern As String = "(?s)^.+"
Dim input As String = "This is one line and" + vbCrLf + "this is the second."
For Each match As Match In Regex.Matches(input, pattern)
Console.WriteLine(Regex.Escape(match.Value))
Next
End Sub
End Module
' The example displays the following output:
' This\ is\ one\ line\ and\r\nthis\ is\ the\ second\.
Pouze explicitní zachytávání
Ve výchozím nastavení jsou zachytávání skupin definovány pomocí závorek ve vzoru regulárního výrazu. Pojmenovaných skupinám se přiřadí název nebo číslo podle možnosti (?< > jazyka dílčího výrazu názvu, zatímco nepojmenované skupiny jsou ) přístupné pomocí indexu. Nepojmenované skupiny v objektu GroupCollection předcházejí pojmenované skupiny.
Seskupovací konstrukce se často používají pouze k použití kvantifikátorů na více prvků jazyka a zachycené podřetězce nejsou zajímavé. Pokud je například následující regulární výraz:
\b\(?((\w+),?\s?)+[\.!?]\)?
je určen pouze k extrakci vět, které končí tečkou, vykřičníkem nebo otazníkem z dokumentu, zajímá se pouze výsledná věta (která je reprezentována Match objektem). Jednotlivá slova v kolekci nejsou.
Zachytávání skupin, které nejsou následně použity, může být nákladné, protože modul regulárních výrazů musí naplnit GroupCollection objekty CaptureCollection kolekce i . Alternativně můžete pomocí možnosti nebo vložené možnosti určit, že jediné platné zachycení jsou explicitně pojmenované nebo očíslované skupiny, které jsou určené konstruktorem RegexOptions.ExplicitCapture n (?< > dílčího výrazu ) name.
Následující příklad zobrazí informace o shodách vrácených vzorem regulárního výrazu při volání metody s možností \b\(?((\w+),?\s?)+[\.!?]\)? Match a bez RegexOptions.ExplicitCapture ní. Jak ukazuje výstup prvního volání metody, modul regulárních výrazů plně naplní objekty kolekce a informacemi o GroupCollection CaptureCollection zachycených podřetězcích. Vzhledem k tomu, že druhá metoda je volána options s nastavenou na RegexOptions.ExplicitCapture , nezachycuje informace o skupinách.
using System;
using System.Text.RegularExpressions;
public class Example
{
public static void Main()
{
string input = "This is the first sentence. Is it the beginning " +
"of a literary masterpiece? I think not. Instead, " +
"it is a nonsensical paragraph.";
string pattern = @"\b\(?((?>\w+),?\s?)+[\.!?]\)?";
Console.WriteLine("With implicit captures:");
foreach (Match match in Regex.Matches(input, pattern))
{
Console.WriteLine("The match: {0}", match.Value);
int groupCtr = 0;
foreach (Group group in match.Groups)
{
Console.WriteLine(" Group {0}: {1}", groupCtr, group.Value);
groupCtr++;
int captureCtr = 0;
foreach (Capture capture in group.Captures)
{
Console.WriteLine(" Capture {0}: {1}", captureCtr, capture.Value);
captureCtr++;
}
}
}
Console.WriteLine();
Console.WriteLine("With explicit captures only:");
foreach (Match match in Regex.Matches(input, pattern, RegexOptions.ExplicitCapture))
{
Console.WriteLine("The match: {0}", match.Value);
int groupCtr = 0;
foreach (Group group in match.Groups)
{
Console.WriteLine(" Group {0}: {1}", groupCtr, group.Value);
groupCtr++;
int captureCtr = 0;
foreach (Capture capture in group.Captures)
{
Console.WriteLine(" Capture {0}: {1}", captureCtr, capture.Value);
captureCtr++;
}
}
}
}
}
// The example displays the following output:
// With implicit captures:
// The match: This is the first sentence.
// Group 0: This is the first sentence.
// Capture 0: This is the first sentence.
// Group 1: sentence
// Capture 0: This
// Capture 1: is
// Capture 2: the
// Capture 3: first
// Capture 4: sentence
// Group 2: sentence
// Capture 0: This
// Capture 1: is
// Capture 2: the
// Capture 3: first
// Capture 4: sentence
// The match: Is it the beginning of a literary masterpiece?
// Group 0: Is it the beginning of a literary masterpiece?
// Capture 0: Is it the beginning of a literary masterpiece?
// Group 1: masterpiece
// Capture 0: Is
// Capture 1: it
// Capture 2: the
// Capture 3: beginning
// Capture 4: of
// Capture 5: a
// Capture 6: literary
// Capture 7: masterpiece
// Group 2: masterpiece
// Capture 0: Is
// Capture 1: it
// Capture 2: the
// Capture 3: beginning
// Capture 4: of
// Capture 5: a
// Capture 6: literary
// Capture 7: masterpiece
// The match: I think not.
// Group 0: I think not.
// Capture 0: I think not.
// Group 1: not
// Capture 0: I
// Capture 1: think
// Capture 2: not
// Group 2: not
// Capture 0: I
// Capture 1: think
// Capture 2: not
// The match: Instead, it is a nonsensical paragraph.
// Group 0: Instead, it is a nonsensical paragraph.
// Capture 0: Instead, it is a nonsensical paragraph.
// Group 1: paragraph
// Capture 0: Instead,
// Capture 1: it
// Capture 2: is
// Capture 3: a
// Capture 4: nonsensical
// Capture 5: paragraph
// Group 2: paragraph
// Capture 0: Instead
// Capture 1: it
// Capture 2: is
// Capture 3: a
// Capture 4: nonsensical
// Capture 5: paragraph
//
// With explicit captures only:
// The match: This is the first sentence.
// Group 0: This is the first sentence.
// Capture 0: This is the first sentence.
// The match: Is it the beginning of a literary masterpiece?
// Group 0: Is it the beginning of a literary masterpiece?
// Capture 0: Is it the beginning of a literary masterpiece?
// The match: I think not.
// Group 0: I think not.
// Capture 0: I think not.
// The match: Instead, it is a nonsensical paragraph.
// Group 0: Instead, it is a nonsensical paragraph.
// Capture 0: Instead, it is a nonsensical paragraph.
Imports System.Text.RegularExpressions
Module Example
Public Sub Main()
Dim input As String = "This is the first sentence. Is it the beginning " + _
"of a literary masterpiece? I think not. Instead, " + _
"it is a nonsensical paragraph."
Dim pattern As String = "\b\(?((?>\w+),?\s?)+[\.!?]\)?"
Console.WriteLine("With implicit captures:")
For Each match As Match In Regex.Matches(input, pattern)
Console.WriteLine("The match: {0}", match.Value)
Dim groupCtr As Integer = 0
For Each group As Group In match.Groups
Console.WriteLine(" Group {0}: {1}", groupCtr, group.Value)
groupCtr += 1
Dim captureCtr As Integer = 0
For Each capture As Capture In group.Captures
Console.WriteLine(" Capture {0}: {1}", captureCtr, capture.Value)
captureCtr += 1
Next
Next
Next
Console.WriteLine()
Console.WriteLine("With explicit captures only:")
For Each match As Match In Regex.Matches(input, pattern, RegexOptions.ExplicitCapture)
Console.WriteLine("The match: {0}", match.Value)
Dim groupCtr As Integer = 0
For Each group As Group In match.Groups
Console.WriteLine(" Group {0}: {1}", groupCtr, group.Value)
groupCtr += 1
Dim captureCtr As Integer = 0
For Each capture As Capture In group.Captures
Console.WriteLine(" Capture {0}: {1}", captureCtr, capture.Value)
captureCtr += 1
Next
Next
Next
End Sub
End Module
' The example displays the following output:
' With implicit captures:
' The match: This is the first sentence.
' Group 0: This is the first sentence.
' Capture 0: This is the first sentence.
' Group 1: sentence
' Capture 0: This
' Capture 1: is
' Capture 2: the
' Capture 3: first
' Capture 4: sentence
' Group 2: sentence
' Capture 0: This
' Capture 1: is
' Capture 2: the
' Capture 3: first
' Capture 4: sentence
' The match: Is it the beginning of a literary masterpiece?
' Group 0: Is it the beginning of a literary masterpiece?
' Capture 0: Is it the beginning of a literary masterpiece?
' Group 1: masterpiece
' Capture 0: Is
' Capture 1: it
' Capture 2: the
' Capture 3: beginning
' Capture 4: of
' Capture 5: a
' Capture 6: literary
' Capture 7: masterpiece
' Group 2: masterpiece
' Capture 0: Is
' Capture 1: it
' Capture 2: the
' Capture 3: beginning
' Capture 4: of
' Capture 5: a
' Capture 6: literary
' Capture 7: masterpiece
' The match: I think not.
' Group 0: I think not.
' Capture 0: I think not.
' Group 1: not
' Capture 0: I
' Capture 1: think
' Capture 2: not
' Group 2: not
' Capture 0: I
' Capture 1: think
' Capture 2: not
' The match: Instead, it is a nonsensical paragraph.
' Group 0: Instead, it is a nonsensical paragraph.
' Capture 0: Instead, it is a nonsensical paragraph.
' Group 1: paragraph
' Capture 0: Instead,
' Capture 1: it
' Capture 2: is
' Capture 3: a
' Capture 4: nonsensical
' Capture 5: paragraph
' Group 2: paragraph
' Capture 0: Instead
' Capture 1: it
' Capture 2: is
' Capture 3: a
' Capture 4: nonsensical
' Capture 5: paragraph
'
' With explicit captures only:
' The match: This is the first sentence.
' Group 0: This is the first sentence.
' Capture 0: This is the first sentence.
' The match: Is it the beginning of a literary masterpiece?
' Group 0: Is it the beginning of a literary masterpiece?
' Capture 0: Is it the beginning of a literary masterpiece?
' The match: I think not.
' Group 0: I think not.
' Capture 0: I think not.
' The match: Instead, it is a nonsensical paragraph.
' Group 0: Instead, it is a nonsensical paragraph.
' Capture 0: Instead, it is a nonsensical paragraph.
Vzor regulárního \b\(?((?>\w+),?\s?)+[\.!?]\)? výrazu je definován tak, jak je znázorněno v následující tabulce.
| Vzor | Popis |
|---|---|
\b |
Začněte na hranici slova. |
\(? |
Porovná žádný nebo jeden výskyt počáteční závorky ("("). |
(?>\w+),? |
Porovná jeden nebo více znaků slova následovaných žádnou nebo jednou čárkou. Při porovnávání znaků slova nevracení zpět. |
\s? |
Porovná žádný nebo jeden prázdný znak. |
((\w+),?\s?)+ |
Porovná kombinaci jednoho nebo více znaků slova, nula nebo jedna čárka a nula nebo jeden prázdné znaky jednou nebo vícekrát. |
[\.!?]\)? |
Porovná kterýkoli ze tří symbolů interpunkce následovaných žádnou nebo jednou uzavírací závorkou (")"). |
Můžete také použít vložený (?n) element k potlačení automatických zachycení. Následující příklad upraví předchozí vzor regulárního výrazu tak, aby místo možnosti byl vložený (?n) RegexOptions.ExplicitCapture prvek.
using System;
using System.Text.RegularExpressions;
public class Example
{
public static void Main()
{
string input = "This is the first sentence. Is it the beginning " +
"of a literary masterpiece? I think not. Instead, " +
"it is a nonsensical paragraph.";
string pattern = @"(?n)\b\(?((?>\w+),?\s?)+[\.!?]\)?";
foreach (Match match in Regex.Matches(input, pattern))
{
Console.WriteLine("The match: {0}", match.Value);
int groupCtr = 0;
foreach (Group group in match.Groups)
{
Console.WriteLine(" Group {0}: {1}", groupCtr, group.Value);
groupCtr++;
int captureCtr = 0;
foreach (Capture capture in group.Captures)
{
Console.WriteLine(" Capture {0}: {1}", captureCtr, capture.Value);
captureCtr++;
}
}
}
}
}
// The example displays the following output:
// The match: This is the first sentence.
// Group 0: This is the first sentence.
// Capture 0: This is the first sentence.
// The match: Is it the beginning of a literary masterpiece?
// Group 0: Is it the beginning of a literary masterpiece?
// Capture 0: Is it the beginning of a literary masterpiece?
// The match: I think not.
// Group 0: I think not.
// Capture 0: I think not.
// The match: Instead, it is a nonsensical paragraph.
// Group 0: Instead, it is a nonsensical paragraph.
// Capture 0: Instead, it is a nonsensical paragraph.
Imports System.Text.RegularExpressions
Module Example
Public Sub Main()
Dim input As String = "This is the first sentence. Is it the beginning " + _
"of a literary masterpiece? I think not. Instead, " + _
"it is a nonsensical paragraph."
Dim pattern As String = "(?n)\b\(?((?>\w+),?\s?)+[\.!?]\)?"
For Each match As Match In Regex.Matches(input, pattern)
Console.WriteLine("The match: {0}", match.Value)
Dim groupCtr As Integer = 0
For Each group As Group In match.Groups
Console.WriteLine(" Group {0}: {1}", groupCtr, group.Value)
groupCtr += 1
Dim captureCtr As Integer = 0
For Each capture As Capture In group.Captures
Console.WriteLine(" Capture {0}: {1}", captureCtr, capture.Value)
captureCtr += 1
Next
Next
Next
End Sub
End Module
' The example displays the following output:
' The match: This is the first sentence.
' Group 0: This is the first sentence.
' Capture 0: This is the first sentence.
' The match: Is it the beginning of a literary masterpiece?
' Group 0: Is it the beginning of a literary masterpiece?
' Capture 0: Is it the beginning of a literary masterpiece?
' The match: I think not.
' Group 0: I think not.
' Capture 0: I think not.
' The match: Instead, it is a nonsensical paragraph.
' Group 0: Instead, it is a nonsensical paragraph.
' Capture 0: Instead, it is a nonsensical paragraph.
Nakonec můžete pomocí elementu vložené skupiny potlačit automatické zachytávání pro (?n:) seskupení podle skupin. Následující příklad upraví předchozí vzor tak, aby potlačil nepojmenované zachycení ve vnější skupině ((?>\w+),?\s?) . Všimněte si, že tím se potlačí nepojmenovaná zachytávání také ve vnitřní skupině.
using System;
using System.Text.RegularExpressions;
public class Example
{
public static void Main()
{
string input = "This is the first sentence. Is it the beginning " +
"of a literary masterpiece? I think not. Instead, " +
"it is a nonsensical paragraph.";
string pattern = @"\b\(?(?n:(?>\w+),?\s?)+[\.!?]\)?";
foreach (Match match in Regex.Matches(input, pattern))
{
Console.WriteLine("The match: {0}", match.Value);
int groupCtr = 0;
foreach (Group group in match.Groups)
{
Console.WriteLine(" Group {0}: {1}", groupCtr, group.Value);
groupCtr++;
int captureCtr = 0;
foreach (Capture capture in group.Captures)
{
Console.WriteLine(" Capture {0}: {1}", captureCtr, capture.Value);
captureCtr++;
}
}
}
}
}
// The example displays the following output:
// The match: This is the first sentence.
// Group 0: This is the first sentence.
// Capture 0: This is the first sentence.
// The match: Is it the beginning of a literary masterpiece?
// Group 0: Is it the beginning of a literary masterpiece?
// Capture 0: Is it the beginning of a literary masterpiece?
// The match: I think not.
// Group 0: I think not.
// Capture 0: I think not.
// The match: Instead, it is a nonsensical paragraph.
// Group 0: Instead, it is a nonsensical paragraph.
// Capture 0: Instead, it is a nonsensical paragraph.
Imports System.Text.RegularExpressions
Module Example
Public Sub Main()
Dim input As String = "This is the first sentence. Is it the beginning " + _
"of a literary masterpiece? I think not. Instead, " + _
"it is a nonsensical paragraph."
Dim pattern As String = "\b\(?(?n:(?>\w+),?\s?)+[\.!?]\)?"
For Each match As Match In Regex.Matches(input, pattern)
Console.WriteLine("The match: {0}", match.Value)
Dim groupCtr As Integer = 0
For Each group As Group In match.Groups
Console.WriteLine(" Group {0}: {1}", groupCtr, group.Value)
groupCtr += 1
Dim captureCtr As Integer = 0
For Each capture As Capture In group.Captures
Console.WriteLine(" Capture {0}: {1}", captureCtr, capture.Value)
captureCtr += 1
Next
Next
Next
End Sub
End Module
' The example displays the following output:
' The match: This is the first sentence.
' Group 0: This is the first sentence.
' Capture 0: This is the first sentence.
' The match: Is it the beginning of a literary masterpiece?
' Group 0: Is it the beginning of a literary masterpiece?
' Capture 0: Is it the beginning of a literary masterpiece?
' The match: I think not.
' Group 0: I think not.
' Capture 0: I think not.
' The match: Instead, it is a nonsensical paragraph.
' Group 0: Instead, it is a nonsensical paragraph.
' Capture 0: Instead, it is a nonsensical paragraph.
Zkompilované regulární výrazy
Ve výchozím nastavení jsou regulární výrazy v rozhraní .NET interpretovány. Při vytvoření instance objektu nebo volání statické metody se vzor regulárního výrazu parsuje do sady vlastních operačních kódů a interpret používá tyto operační kódy ke spuštění Regex Regex regulárního výrazu. To zahrnuje kompromis: Náklady na inicializaci modulu regulárních výrazů jsou minimalizovány na úkor výkonu za běhu.
Pomocí parametru můžete místo interpretovaných regulárních výrazů použít zkompilované RegexOptions.Compiled výrazy. V tomto případě se vzor předá modulu regulárních výrazů, parsuje se do sady operačních kódů a pak se převede do jazyka MSIL (Microsoft Intermediate Language), který lze předat přímo modulu CLR (Common Language Runtime). Zkompilované regulární výrazy maximalizují výkon za běhu na úkor času inicializace.
Poznámka
Regulární výraz lze zkompilovat pouze poskytnutím hodnoty parametru konstruktoru třídy nebo statické RegexOptions.Compiled options metody porovnávání Regex vzorů. Není k dispozici jako vložené možnosti.
Zkompilované regulární výrazy můžete použít ve volání statických i instancí regulárních výrazů. Ve statických regulárních výrazech je parametr předán parametru metody porovnávání RegexOptions.Compiled options vzorů regulárního výrazu. V případě regulárních výrazů se předá do options parametru Regex konstruktoru třídy. V obou případech to vede ke zvýšení výkonu.
Toto zlepšení výkonu však probíhá pouze za následujících podmínek:
Objekt, který představuje konkrétní regulární výraz, se používá ve více voláních metod porovnávání Regex vzorů regulárních výrazů.
Objekt nemůže být mimo rozsah, takže ho můžete Regex znovu použít.
Statický regulární výraz se používá ve více voláních metod porovnávání vzorů regulárních výrazů. (Zvýšení výkonu je možné, protože regulární výrazy používané ve volání statických metod jsou uloženy v mezipaměti strojem regulárních výrazů.)
Poznámka
Možnost nesouvisí s metodou , která vytvoří sestavení pro zvláštní účely, RegexOptions.Compiled Regex.CompileToAssembly které obsahuje předdefinované zkompilované regulární výrazy.
Ignorování mezer
Ve výchozím nastavení jsou prázdné znaky ve vzoru regulárního výrazu významné. Vynutí modul regulárních výrazů, aby odpovídal prázdnému znaku ve vstupním řetězci. Z tohoto důvodu jsou regulární výrazy " " a \b\w+\s \b\w+ " přibližně ekvivalentními regulárními výrazy. Kromě toho se při použití znaku čísla (#) ve vzoru regulárního výrazu interpretuje jako literálový znak, který se má spárovat.
Možnost RegexOptions.IgnorePatternWhitespace nebo možnost x Inline (Vložený) změní toto výchozí chování následujícím způsobem:
Neuměněné prázdné znaky ve vzoru regulárního výrazu se ignorují. Aby byl vzor regulárního výrazu součástí, musí být prázdné znaky uvozeny (například jako
\snebo "\").Znak čísla (#) se interpretuje jako začátek komentáře, nikoli jako literálový znak. Veškerý text ve vzoru regulárního výrazu od znaku po další znak nebo na konec řetězce
#\nse interpretuje jako komentář.
V následujících případech se však prázdné znaky v regulárním výrazu neignorují, i když použijete RegexOptions.IgnorePatternWhitespace možnost :
Prázdné znaky ve třídě znaků se vždy interpretují doslovně. Například vzor regulárního výrazu odpovídá jednomu prázdnému
[ .,;:]znaku, tečkě, čárce, středníku nebo dvojtečku.Prázdné znaky nejsou povoleny v kvantifikátoru v závorkách, například
{n, n a}{,}{n,m}. Vzor regulárního výrazu například nedokáže spárovat žádné sekvence číslic z jedné na tři číslice, protože obsahuje\d{1, 3}prázdné znaky.Prázdné znaky nejsou povoleny v rámci sekvence znaků, která zavádí prvek jazyka. Například:
Dílčí výraz
(?:elementu jazyka představuje skupinu, která nezachytá, a část elementu nemůže mít)vložené(?:mezery. Dílčí výraz vzoru vyvolá za běhu , protože modul regulárních výrazů nemůže vzor parsovat a dílčí výraz vzoru neodpovídá dílčímu(? :)ArgumentException( ?:)výrazu.Název elementu jazyka , který představuje kategorii Unicode nebo pojmenovaný blok, nemůže v části elementu obsahovat vložené
\p{}\p{mezery. Pokud zahrníte prázdné znaky, vyvolá prvek za ArgumentException běhu .
Povolení této možnosti pomáhá zjednodušit regulární výrazy, které se často obtížně parsují a jsou srozumitelné. Zlepšuje čitelnost a umožňuje zdokumentovat regulární výraz.
Následující příklad definuje následující vzor regulárního výrazu:
\b \(? ( (?>\w+) ,?\s? )+ [\.!?] \)? # Matches an entire sentence.
Tento vzor se podobá vzoru definovanému v části Pouze explicitní zachycení s tím rozdílem, že pomocí možnosti RegexOptions.IgnorePatternWhitespace ignoruje prázdné znaky vzoru.
using System;
using System.Text.RegularExpressions;
public class Example
{
public static void Main()
{
string input = "This is the first sentence. Is it the beginning " +
"of a literary masterpiece? I think not. Instead, " +
"it is a nonsensical paragraph.";
string pattern = @"\b \(? ( (?>\w+) ,?\s? )+ [\.!?] \)? # Matches an entire sentence.";
foreach (Match match in Regex.Matches(input, pattern, RegexOptions.IgnorePatternWhitespace))
Console.WriteLine(match.Value);
}
}
// The example displays the following output:
// This is the first sentence.
// Is it the beginning of a literary masterpiece?
// I think not.
// Instead, it is a nonsensical paragraph.
Imports System.Text.RegularExpressions
Module Example
Public Sub Main()
Dim input As String = "This is the first sentence. Is it the beginning " + _
"of a literary masterpiece? I think not. Instead, " + _
"it is a nonsensical paragraph."
Dim pattern As String = "\b \(? ( (?>\w+) ,?\s? )+ [\.!?] \)? # Matches an entire sentence."
For Each match As Match In Regex.Matches(input, pattern, RegexOptions.IgnorePatternWhitespace)
Console.WriteLine(match.Value)
Next
End Sub
End Module
' The example displays the following output:
' This is the first sentence.
' Is it the beginning of a literary masterpiece?
' I think not.
' Instead, it is a nonsensical paragraph.
Následující příklad používá možnost inline k (?x) ignorování prázdného vzoru.
using System;
using System.Text.RegularExpressions;
public class Example
{
public static void Main()
{
string input = "This is the first sentence. Is it the beginning " +
"of a literary masterpiece? I think not. Instead, " +
"it is a nonsensical paragraph.";
string pattern = @"(?x)\b \(? ( (?>\w+) ,?\s? )+ [\.!?] \)? # Matches an entire sentence.";
foreach (Match match in Regex.Matches(input, pattern))
Console.WriteLine(match.Value);
}
}
// The example displays the following output:
// This is the first sentence.
// Is it the beginning of a literary masterpiece?
// I think not.
// Instead, it is a nonsensical paragraph.
Imports System.Text.RegularExpressions
Module Example
Public Sub Main()
Dim input As String = "This is the first sentence. Is it the beginning " + _
"of a literary masterpiece? I think not. Instead, " + _
"it is a nonsensical paragraph."
Dim pattern As String = "(?x)\b \(? ( (?>\w+) ,?\s? )+ [\.!?] \)? # Matches an entire sentence."
For Each match As Match In Regex.Matches(input, pattern)
Console.WriteLine(match.Value)
Next
End Sub
End Module
' The example displays the following output:
' This is the first sentence.
' Is it the beginning of a literary masterpiece?
' I think not.
' Instead, it is a nonsensical paragraph.
Režim se šipkami zprava doleva
Ve výchozím nastavení hledá modul regulárních výrazů zleva doprava. Směr hledání můžete obrátit pomocí RegexOptions.RightToLeft možnosti . Hledání automaticky začíná na poslední pozici znaku řetězce. U metod porovnávání vzorů, které zahrnují parametr počáteční pozice, například , je počáteční pozice indexem pozice znaku nejvíce vpravo, na které má Regex.Match(String, Int32) vyhledávání začít.
Poznámka
Režim vzoru zprava doleva je k dispozici pouze poskytnutím hodnoty parametru konstruktoru třídy nebo statické RegexOptions.RightToLeft options metody porovnávání Regex vzorů. Není k dispozici jako vložené možnosti.
Možnost RegexOptions.RightToLeft změní pouze směr hledání; ne interpretuje vzor regulárního výrazu zprava doleva. Například regulární výraz odpovídá slovům, která začínají písmenem "b" a jsou následovaná \bb\w+\s mezerou. V následujícím příkladu se vstupní řetězec skládá ze tří slov, která obsahují jeden nebo více znaků "b". První slovo začíná písmenem "b", druhé končí na "b" a třetí obsahuje dva znaky "b" uprostřed slova. Jak ukazuje výstup z příkladu, shoduje se se vzorem regulárního výrazu pouze první slovo.
using System;
using System.Text.RegularExpressions;
public class Example
{
public static void Main()
{
string pattern = @"\bb\w+\s";
string input = "builder rob rabble";
foreach (Match match in Regex.Matches(input, pattern, RegexOptions.RightToLeft))
Console.WriteLine("'{0}' found at position {1}.", match.Value, match.Index);
}
}
// The example displays the following output:
// 'builder ' found at position 0.
Imports System.Text.RegularExpressions
Module Example
Public Sub Main()
Dim pattern As String = "\bb\w+\s"
Dim input As String = "builder rob rabble"
For Each match As Match In Regex.Matches(input, pattern, RegexOptions.RightToLeft)
Console.WriteLine("'{0}' found at position {1}.", match.Value, match.Index)
Next
End Sub
End Module
' The example displays the following output:
' 'builder ' found at position 0.
Všimněte si také, že kontrolní výraz vyhledávání (element jazyka dílčího výrazu) a kontrolní výraz (?= ) lookbehind (element (?<= jazyka podvýrazu) nemění ) směr. Kontrolní výrazy lookahead vypadají napravo. Kontrolní výrazy lookbehind vypadají doleva. Například regulární výraz používá kontrolní výraz lookbehind k otestování data, (?<=\d{1,2}\s)\w+,?\s\d{4} které předchází názvu měsíce. Regulární výraz pak odpovídá měsíci a roku. Informace o kontrolních výrazech vyhledávání a vyhledávání najdete v tématu Seskupovací konstrukce.
using System;
using System.Text.RegularExpressions;
public class Example
{
public static void Main()
{
string[] inputs = { "1 May 1917", "June 16, 2003" };
string pattern = @"(?<=\d{1,2}\s)\w+,?\s\d{4}";
foreach (string input in inputs)
{
Match match = Regex.Match(input, pattern, RegexOptions.RightToLeft);
if (match.Success)
Console.WriteLine("The date occurs in {0}.", match.Value);
else
Console.WriteLine("{0} does not match.", input);
}
}
}
// The example displays the following output:
// The date occurs in May 1917.
// June 16, 2003 does not match.
Imports System.Text.RegularExpressions
Module Example
Public Sub Main()
Dim inputs() As String = {"1 May 1917", "June 16, 2003"}
Dim pattern As String = "(?<=\d{1,2}\s)\w+,?\s\d{4}"
For Each input As String In inputs
Dim match As Match = Regex.Match(input, pattern, RegexOptions.RightToLeft)
If match.Success Then
Console.WriteLine("The date occurs in {0}.", match.Value)
Else
Console.WriteLine("{0} does not match.", input)
End If
Next
End Sub
End Module
' The example displays the following output:
' The date occurs in May 1917.
' June 16, 2003 does not match.
Vzor regulárního výrazu je definován tak, jak je znázorněno v následující tabulce.
| Vzor | Popis |
|---|---|
(?<=\d{1,2}\s) |
Před začátkem shody musí být jedna nebo dvě desítkové číslice následované mezerou. |
\w+ |
Porovná jeden nebo více znaků slova. |
,? |
Porovná žádný nebo jeden znak čárky. |
\s |
Porovná prázdný znak. |
\d{4} |
Porovná čtyři desítkové číslice. |
Chování při porovnávání ECMAScriptu
Ve výchozím nastavení používá modul regulárních výrazů kanonické chování při porovnávání vzoru regulárního výrazu se vstupním textem. Můžete ale instruovat modul regulárních výrazů, aby pomocí odpovídajícího chování ECMAScriptu zadál RegexOptions.ECMAScript možnost .
Poznámka
Chování kompatibilní s ECMAScriptem je k dispozici pouze poskytnutím hodnoty parametru konstruktoru třídy nebo statické RegexOptions.ECMAScript options metody porovnávání Regex vzorů. Není k dispozici jako vložené možnosti.
Možnost RegexOptions.ECMAScript lze kombinovat pouze s RegexOptions.IgnoreCase možnostmi a RegexOptions.Multiline . Použití jakékoli jiné možnosti v regulárním výrazu má za výsledek ArgumentOutOfRangeException .
Chování ECMAScriptu a kanonických regulárních výrazů se liší ve třech oblastech: syntaxe třídy znaků, vlastní odkazování na zachytávající skupiny a osmičkové a backreference interpretace.
Syntaxe třídy znaků. Vzhledem k tomu, že kanonické regulární výrazy podporují Unicode, zatímco ECMAScript ne, mají třídy znaků v ECMAScriptu omezenější syntaxi a některé prvky jazyka třídy znaků mají jiný význam. Například ECMAScript nepodporuje prvky jazyka, jako je kategorie Unicode nebo elementy bloku
\pa\P. Podobně je prvek, který odpovídá znaku slova, ekvivalentní třídě znaků při použití\wjazyka ECMAScript a při[a-zA-Z_0-9]použití[\p{Ll}\p{Lu}\p{Lt}\p{Lo}\p{Nd}\p{Pc}\p{Lm}]kanonického chování. Další informace najdete v tématu Třídy znaků.Následující příklad ukazuje rozdíl mezi porovnáváním vzorů kanonických vzorů a vzorů ECMAScript. Definuje regulární výraz , který odpovídá slovům
\b(\w+\s*)+následovaných mezerami. Vstup se skládá ze dvou řetězců, jednoho, který používá znakovou sadu latinky, a druhého, který používá znakovou sadu cyrilice. Jak ukazuje výstup, volání metody, která používá porovnávání ECMAScriptu, neodpovídá slovům cyrilice, zatímco volání metody, které používá kanonické porovnávání, odpovídá Regex.IsMatch(String, String, RegexOptions) těmto slovům.using System; using System.Text.RegularExpressions; public class Example { public static void Main() { string[] values = { "целый мир", "the whole world" }; string pattern = @"\b(\w+\s*)+"; foreach (var value in values) { Console.Write("Canonical matching: "); if (Regex.IsMatch(value, pattern)) Console.WriteLine("'{0}' matches the pattern.", value); else Console.WriteLine("{0} does not match the pattern.", value); Console.Write("ECMAScript matching: "); if (Regex.IsMatch(value, pattern, RegexOptions.ECMAScript)) Console.WriteLine("'{0}' matches the pattern.", value); else Console.WriteLine("{0} does not match the pattern.", value); Console.WriteLine(); } } } // The example displays the following output: // Canonical matching: 'целый мир' matches the pattern. // ECMAScript matching: целый мир does not match the pattern. // // Canonical matching: 'the whole world' matches the pattern. // ECMAScript matching: 'the whole world' matches the pattern.Imports System.Text.RegularExpressions Module Example Public Sub Main() Dim values() As String = {"целый мир", "the whole world"} Dim pattern As String = "\b(\w+\s*)+" For Each value In values Console.Write("Canonical matching: ") If Regex.IsMatch(value, pattern) Console.WriteLine("'{0}' matches the pattern.", value) Else Console.WriteLine("{0} does not match the pattern.", value) End If Console.Write("ECMAScript matching: ") If Regex.IsMatch(value, pattern, RegexOptions.ECMAScript) Console.WriteLine("'{0}' matches the pattern.", value) Else Console.WriteLine("{0} does not match the pattern.", value) End If Console.WriteLine() Next End Sub End Module ' The example displays the following output: ' Canonical matching: 'целый мир' matches the pattern. ' ECMAScript matching: целый мир does not match the pattern. ' ' Canonical matching: 'the whole world' matches the pattern. ' ECMAScript matching: 'the whole world' matches the pattern.Zachytávání skupin odkazující na sebe. Třída zachycení regulárního výrazu s zpětným odkazem na sebe sama musí být aktualizována každou iterací zachycení. Jak ukazuje následující příklad, tato funkce umožňuje, aby regulární výraz při použití ECMAScriptu odpovídal vstupnímu řetězci
((a+)(\1) ?)+"aa aaaaa aaaaaa", ale ne při použití kanonické shody.using System; using System.Text.RegularExpressions; public class Example { static string pattern; public static void Main() { string input = "aa aaaa aaaaaa "; pattern = @"((a+)(\1) ?)+"; // Match input using canonical matching. AnalyzeMatch(Regex.Match(input, pattern)); // Match input using ECMAScript. AnalyzeMatch(Regex.Match(input, pattern, RegexOptions.ECMAScript)); } private static void AnalyzeMatch(Match m) { if (m.Success) { Console.WriteLine("'{0}' matches {1} at position {2}.", pattern, m.Value, m.Index); int grpCtr = 0; foreach (Group grp in m.Groups) { Console.WriteLine(" {0}: '{1}'", grpCtr, grp.Value); grpCtr++; int capCtr = 0; foreach (Capture cap in grp.Captures) { Console.WriteLine(" {0}: '{1}'", capCtr, cap.Value); capCtr++; } } } else { Console.WriteLine("No match found."); } Console.WriteLine(); } } // The example displays the following output: // No match found. // // '((a+)(\1) ?)+' matches aa aaaa aaaaaa at position 0. // 0: 'aa aaaa aaaaaa ' // 0: 'aa aaaa aaaaaa ' // 1: 'aaaaaa ' // 0: 'aa ' // 1: 'aaaa ' // 2: 'aaaaaa ' // 2: 'aa' // 0: 'aa' // 1: 'aa' // 2: 'aa' // 3: 'aaaa ' // 0: '' // 1: 'aa ' // 2: 'aaaa 'Imports System.Text.RegularExpressions Module Example Dim pattern As String Public Sub Main() Dim input As String = "aa aaaa aaaaaa " pattern = "((a+)(\1) ?)+" ' Match input using canonical matching. AnalyzeMatch(Regex.Match(input, pattern)) ' Match input using ECMAScript. AnalyzeMatch(Regex.Match(input, pattern, RegexOptions.ECMAScript)) End Sub Private Sub AnalyzeMatch(m As Match) If m.Success Console.WriteLine("'{0}' matches {1} at position {2}.", _ pattern, m.Value, m.Index) Dim grpCtr As Integer = 0 For Each grp As Group In m.Groups Console.WriteLine(" {0}: '{1}'", grpCtr, grp.Value) grpCtr += 1 Dim capCtr As Integer = 0 For Each cap As Capture In grp.Captures Console.WriteLine(" {0}: '{1}'", capCtr, cap.Value) capCtr += 1 Next Next Else Console.WriteLine("No match found.") End If Console.WriteLine() End Sub End Module ' The example displays the following output: ' No match found. ' ' '((a+)(\1) ?)+' matches aa aaaa aaaaaa at position 0. ' 0: 'aa aaaa aaaaaa ' ' 0: 'aa aaaa aaaaaa ' ' 1: 'aaaaaa ' ' 0: 'aa ' ' 1: 'aaaa ' ' 2: 'aaaaaa ' ' 2: 'aa' ' 0: 'aa' ' 1: 'aa' ' 2: 'aa' ' 3: 'aaaa ' ' 0: '' ' 1: 'aa ' ' 2: 'aaaa 'Regulární výraz je definován tak, jak je znázorněno v následující tabulce.
Vzor Popis (a+) Porovná jedno nebo vícekrát písmeno "a". Toto je druhá zachytávající skupina. (\1) Porovná podřetězec zachycený první zachytávající skupinou. Toto je třetí zachytávající skupina. ? Porovná žádný nebo jeden znak mezery. ((a+)(\1) ?) + Porovná vzor jednoho nebo více znaků "a" následovaných řetězcem, který odpovídá první zachytávající skupině následované jedním nebo více znaky mezery. Toto je první zachytávající skupina. Řešení nejednoznačností mezi osmičkovým řídicím znakem a zpětnými odkazy Následující tabulka shrnuje rozdíly v osmičkové interpretaci a interpretaci zpětných odkazů pomocí kanonických a ECMAScriptových regulárních výrazů.
Regulární výraz Kanonické chování Chování ECMAScriptu \0Následované 0 až 2 osmičkální číslicemiInterpretuje se jako osmičkové. Například se \044vždy interpretuje jako osmičkové hodnoty a znamená "$".Stejné chování. \za ním následuje číslice od 1 do 9 a za ním žádné další desítkové číslice.Interpretuje se jako zpětný odkaz. Například vždy znamená zpětný odkaz 9, i když devátá zachytávající skupina \9neexistuje. Pokud zachytávající skupina neexistuje, analyzátor regulárních výrazů vyvolá ArgumentException .Pokud existuje jedna zachytávající skupina desítkových číslic, zpětný odkaz na číslici. Jinak interpretuje hodnotu jako literál. \Za ním následuje číslice od 1 do 9, za kterou následují další desítkové číslice.Interpretuje číslice jako desetinnou hodnotu. Pokud tato zachytávající skupina existuje, interpretuje výraz jako zpětný odkaz.
Jinak interpretovat počáteční osmičkové číslice až do osmičkové 377; To znamená, že vezměte v úvahu pouze nízkých 8 bitů hodnoty. Zbývající číslice se interpretují jako literály. Pokud například ve výrazu existuje zachytávající skupina 300, interpretuje se jako zpětný odkaz 300. Pokud zachytávání skupiny 300 neexistuje, interpretuje se jako\3000osmičkové 300 následované 0.Interpretujte jako zpětný odkaz tak, že převedete co nejvíce číslic na desetinnou hodnotu, která může odkazovat na zachycení. Pokud nelze převést žádné číslice, interpretuje se jako osmičkové číslo pomocí počátečních osmičkové číslice až do osmičkové hodnoty 377. interpretuje zbývající číslice jako literály.
Porovnání s využitím invariantní jazykové verze
Pokud modul regulárních výrazů provádí porovnání bez rozlišení velkých a malých písmen, používá ve výchozím nastavení konvence použití velkých a malých písmen aktuální jazykové verze k určení ekvivalentních velkých a malých písmen.
Toto chování je však nežádoucí u některých typů porovnání, zejména při porovnávání uživatelského vstupu s názvy systémových prostředků, jako jsou hesla, soubory nebo adresy URL. Následující příklad ilustruje například scénář. Kód je určený k blokování přístupu k libovolnému prostředku, jehož adresa URL má před FILE://. Regulární výraz se pokusí s řetězcem shodovat bez rozlišení velkých a malých písmen pomocí regulárního výrazu $FILE:// . Pokud je ale aktuální systémová jazyková verze tr-TR (turečtina– Turečtina), "I" není velkým ekvivalentem "i". Výsledkem je, že volání metody vrátí a přístup k souboru Regex.IsMatch false je povolený.
CultureInfo defaultCulture = Thread.CurrentThread.CurrentCulture;
Thread.CurrentThread.CurrentCulture = new CultureInfo("tr-TR");
string input = "file://c:/Documents.MyReport.doc";
string pattern = "FILE://";
Console.WriteLine("Culture-sensitive matching ({0} culture)...",
Thread.CurrentThread.CurrentCulture.Name);
if (Regex.IsMatch(input, pattern, RegexOptions.IgnoreCase))
Console.WriteLine("URLs that access files are not allowed.");
else
Console.WriteLine("Access to {0} is allowed.", input);
Thread.CurrentThread.CurrentCulture = defaultCulture;
// The example displays the following output:
// Culture-sensitive matching (tr-TR culture)...
// Access to file://c:/Documents.MyReport.doc is allowed.
Dim defaultCulture As CultureInfo = Thread.CurrentThread.CurrentCulture
Thread.CurrentThread.CurrentCulture = New CultureInfo("tr-TR")
Dim input As String = "file://c:/Documents.MyReport.doc"
Dim pattern As String = "$FILE://"
Console.WriteLine("Culture-sensitive matching ({0} culture)...", _
Thread.CurrentThread.CurrentCulture.Name)
If Regex.IsMatch(input, pattern, RegexOptions.IgnoreCase) Then
Console.WriteLine("URLs that access files are not allowed.")
Else
Console.WriteLine("Access to {0} is allowed.", input)
End If
Thread.CurrentThread.CurrentCulture = defaultCulture
' The example displays the following output:
' Culture-sensitive matching (tr-TR culture)...
' Access to file://c:/Documents.MyReport.doc is allowed.
Poznámka
Další informace o porovnávání řetězců, která rozlišují malá a velká písmena a používají neutrální jazykovou verzi, najdete v tématu Osvědčené postupy pro používání řetězců.
Místo porovnání aktuální jazykové verze bez rozlišení velkých a malých písmen můžete zadat možnost ignorovat kulturní rozdíly v jazyce a používat konvence neutrální RegexOptions.CultureInvariant jazykové verze.
Poznámka
Porovnání pomocí invariantní jazykové verze je k dispozici pouze poskytnutím hodnoty parametru konstruktoru třídy nebo statické RegexOptions.CultureInvariant options metody porovnávání Regex vzorů. Není k dispozici jako vložené možnosti.
Následující příklad je stejný jako v předchozím příkladu s tím rozdílem, že statická metoda je Regex.IsMatch(String, String, RegexOptions) volána s možnostmi, které zahrnují RegexOptions.CultureInvariant . I když je aktuální jazyková verze nastavená na turečtinu (Turečtina), je modul regulárních výrazů schopen úspěšně porovnat "FILE" a "file" a blokovat přístup k prostředku souboru.
CultureInfo defaultCulture = Thread.CurrentThread.CurrentCulture;
Thread.CurrentThread.CurrentCulture = new CultureInfo("tr-TR");
string input = "file://c:/Documents.MyReport.doc";
string pattern = "FILE://";
Console.WriteLine("Culture-insensitive matching...");
if (Regex.IsMatch(input, pattern,
RegexOptions.IgnoreCase | RegexOptions.CultureInvariant))
Console.WriteLine("URLs that access files are not allowed.");
else
Console.WriteLine("Access to {0} is allowed.", input);
Thread.CurrentThread.CurrentCulture = defaultCulture;
// The example displays the following output:
// Culture-insensitive matching...
// URLs that access files are not allowed.
Dim defaultCulture As CultureInfo = Thread.CurrentThread.CurrentCulture
Thread.CurrentThread.CurrentCulture = New CultureInfo("tr-TR")
Dim input As String = "file://c:/Documents.MyReport.doc"
Dim pattern As String = "$FILE://"
Console.WriteLine("Culture-insensitive matching...")
If Regex.IsMatch(input, pattern, _
RegexOptions.IgnoreCase Or RegexOptions.CultureInvariant) Then
Console.WriteLine("URLs that access files are not allowed.")
Else
Console.WriteLine("Access to {0} is allowed.", input)
End If
Thread.CurrentThread.CurrentCulture = defaultCulture
' The example displays the following output:
' Culture-insensitive matching...
' URLs that access files are not allowed.