System.Text.RegularExpressions.Regex sınıfı

Bu makale, bu API'nin başvuru belgelerine ek açıklamalar sağlar.

Regex sınıfı öğesini temsil eder. NET'in normal ifade altyapısı. Bu sınıfı kullanarak:

  • Belirli karakter desenlerini bulmak için büyük miktarda metni hızla ayrıştırın.
  • Metin alt dizelerini ayıklayın, düzenleyin, değiştirin veya silin.
  • Rapor oluşturmak için ayıklanan dizeleri bir koleksiyona ekleyin.

Not

Belirli bir normal ifade desenine uygun olup olmadığını belirleyerek bir dizeyi doğrulamak istiyorsanız sınıfını System.Configuration.RegexStringValidator kullanabilirsiniz.

Normal ifadeleri kullanmak için, normal ifade dili - hızlı başvuru bölümünde belgelenen söz dizimini kullanarak metin akışında tanımlamak istediğiniz deseni tanımlarsınız. Ardından, isteğe bağlı olarak bir Regex nesne örneği oluşturabilirsiniz. Son olarak, normal ifade deseni ile eşleşen metni değiştirme veya desen eşleşmesini tanımlama gibi bazı işlemler gerçekleştiren bir yöntemi çağırırsınız.

Normal ifade dili hakkında daha fazla bilgi için bkz . Normal ifade dili - hızlı başvuru veya şu broşürlerden birini indirip yazdırma:

Word'de Hızlı Başvuru (.docx) biçimindePDF (.pdf) biçiminde Hızlı Başvuru

Regex ile Dize yöntemleri karşılaştırması

sınıfı, System.String metinle desen eşleştirme gerçekleştirmek için kullanabileceğiniz çeşitli arama ve karşılaştırma yöntemleri içerir. Örneğin, String.Contains, String.EndsWithve String.StartsWith yöntemleri bir dize örneğinin belirtilen bir alt dize içerip içermediğini belirler; ve String.IndexOf, String.IndexOfAny, String.LastIndexOfve String.LastIndexOfAny yöntemleri bir dizede belirtilen alt dizenin başlangıç konumunu döndürür. Belirli bir dizeyi System.String ararken sınıfının yöntemlerini kullanın. Dizede Regex belirli bir deseni ararken sınıfını kullanın. Daha fazla bilgi ve örnek için bkz . .NET Normal İfadeleri.

Statik ve örnek yöntemleri karşılaştırması

Normal ifade desenini tanımladıktan sonra, bunu normal ifade altyapısına iki yoldan biriyle sağlayabilirsiniz:

  • Normal ifadeyi temsil eden bir Regex nesne örneği oluşturarak. Bunu yapmak için normal ifade desenini bir Regex oluşturucuya geçirirsiniz. Nesne Regex sabittir; bir Regex nesneyi normal ifadeyle örneklediğinizde, bu nesnenin normal ifadesi değiştirilemez.

  • Hem normal ifadeyi hem de aranacak staticShared metni ( Visual Basic'te) Regex sağlayarak. Bu, açıkça bir nesne oluşturmadan normal bir Regex ifade kullanmanıza olanak tanır.

Tüm Regex desen belirleme yöntemleri hem statik hem de örnek aşırı yüklemelerini içerir.

Desenin kullanılabilmesi için normal ifade altyapısının belirli bir deseni derlemesi gerekir. Nesneler sabit olduğundan Regex , bu bir sınıf oluşturucu veya statik bir yöntem çağrıldığında Regex oluşan tek seferlik bir yordamdır. Tek bir normal ifadeyi tekrar tekrar derleme gereksinimini ortadan kaldırmak için, normal ifade altyapısı statik yöntem çağrılarında kullanılan derlenmiş normal ifadeleri önbelleğe alır. Sonuç olarak, normal ifade desen eşleştirme yöntemleri statik ve örnek yöntemleri için karşılaştırılabilir performans sunar. Ancak önbelleğe alma, aşağıdaki iki durumda performansı olumsuz etkileyebilir:

  • Çok sayıda normal ifadeyle statik yöntem çağrıları kullandığınızda. Varsayılan olarak, normal ifade altyapısı en son kullanılan 15 statik normal ifadeyi önbelleğe alır. Uygulamanız 15'ten fazla statik normal ifade kullanıyorsa, bazı normal ifadelerin yeniden derlenmiş olması gerekir. Bu yeniden derlemeyi önlemek için özelliğini artırabilirsiniz Regex.CacheSize .

  • Daha önce derlenmiş normal ifadelerle yeni Regex nesnelerin örneğini oluştururken. Örneğin, aşağıdaki kod, bir metin akışında yinelenen sözcükleri bulmak için normal bir ifade tanımlar. Örnekte tek bir normal ifade kullanılıyor olsa da, her metin satırını işlemek için yeni Regex bir nesne örneği oluşturur. Bu, normal ifadenin döngünün her yinelemesiyle yeniden derlenmesine neden olur.

    StreamReader sr = new StreamReader(filename);
    string input;
    string pattern = @"\b(\w+)\s\1\b";
    while (sr.Peek() >= 0)
    {
       input = sr.ReadLine();
       Regex rgx = new Regex(pattern, RegexOptions.IgnoreCase);
       MatchCollection matches = rgx.Matches(input);
       if (matches.Count > 0)
       {
          Console.WriteLine("{0} ({1} matches):", input, matches.Count);
          foreach (Match match in matches)
             Console.WriteLine("   " + match.Value);
       }
    }
    sr.Close();
    
    Dim sr As New StreamReader(filename)
    Dim input As String
    Dim pattern As String = "\b(\w+)\s\1\b"
    Do While sr.Peek() >= 0
       input = sr.ReadLine()
       Dim rgx As New Regex(pattern, RegexOptions.IgnoreCase)
       Dim matches As MatchCollection = rgx.Matches(input)
       If matches.Count > 0 Then
          Console.WriteLine("{0} ({1} matches):", input, matches.Count)
          For Each match As Match In matches
             Console.WriteLine("   " + match.Value)
          Next   
       End If
    Loop
    sr.Close()
    

    Yeniden derlemeyi önlemek için, aşağıdaki yeniden yazma örneğinde gösterildiği gibi, bunu gerektiren tüm kodlar için erişilebilir olan tek Regex bir nesne örneği oluşturmanız gerekir.

    StreamReader sr = new StreamReader(filename);
    string input;
    string pattern = @"\b(\w+)\s\1\b";
    Regex rgx = new Regex(pattern, RegexOptions.IgnoreCase);
    
    while (sr.Peek() >= 0)
    {
       input = sr.ReadLine();
       MatchCollection matches = rgx.Matches(input);
       if (matches.Count > 0)
       {
          Console.WriteLine("{0} ({1} matches):", input, matches.Count);
          foreach (Match match in matches)
             Console.WriteLine("   " + match.Value);
       }
    }
    sr.Close();
    
    Dim sr As New StreamReader(filename)
    Dim input As String
    Dim pattern As String = "\b(\w+)\s\1\b"
    Dim rgx As New Regex(pattern, RegexOptions.IgnoreCase)
    Do While sr.Peek() >= 0
       input = sr.ReadLine()
       Dim matches As MatchCollection = rgx.Matches(input)
       If matches.Count > 0 Then
          Console.WriteLine("{0} ({1} matches):", input, matches.Count)
          For Each match As Match In matches
             Console.WriteLine("   " + match.Value)
          Next   
       End If
    Loop
    sr.Close()
    

Normal ifade işlemleri gerçekleştirme

İster bir Regex nesnenin örneğini oluşturup yöntemlerini çağırın, ister statik yöntemleri çağırın Regex , sınıfı aşağıdaki desen eşleştirme işlevselliğini sunar:

  • Eşleşmenin doğrulanması. Bir eşleşme olup olmadığını belirlemek için yöntemini çağırırsınız IsMatch .

  • Tek bir eşleşme alınıyor. Dizedeki Match veya dizenin bir Match bölümündeki ilk eşleşmeyi temsil eden bir nesneyi almak için yöntemini çağırırsınız. Sonraki eşleşmeler yöntemi çağrılarak Match.NextMatch alınabilir.

  • Tüm eşleşmeler alınıyor. Bir dizede veya dizenin Matches bir System.Text.RegularExpressions.MatchCollection bölümünde bulunan tüm eşleşmeleri temsil eden bir nesneyi almak için yöntemini çağırırsınız.

  • Eşleşen metnin değiştirilmesi. Eşleşen metni değiştirmek için yöntemini çağırırsınız Replace . Değiştirme metni normal bir ifadeyle de tanımlanabilir. Ayrıca, bazı Replace yöntemler, değiştirme metnini program aracılığıyla tanımlamanızı sağlayan bir MatchEvaluator parametre içerir.

  • Giriş dizesinin bölümlerinden oluşturulmuş bir dize dizisi oluşturma. Bir giriş dizesini Split normal ifade tarafından tanımlanan konumlara bölmek için yöntemini çağırırsınız.

Sınıfı, Regex desen eşleştirme yöntemlerine ek olarak birkaç özel amaçlı yöntem içerir:

  • yöntemi, Escape normal ifade veya giriş dizesinde normal ifade işleçleri olarak yorumlanabilir tüm karakterlerin kaçışını verir.
  • yöntemi bu Unescape kaçış karakterlerini kaldırır.
  • yöntemi, CompileToAssembly önceden tanımlanmış normal ifadeler içeren bir derleme oluşturur. .NET, ad alanında System.Web.RegularExpressions bu özel amaçlı derlemelerin örneklerini içerir.

Zaman aşımı değeri tanımlama

.NET, desen eşleştirmede önemli güç ve esneklik sağlayan tam özellikli bir normal ifade dilini destekler. Ancak, güç ve esneklik bir maliyetle gelir: düşük performans riski. Düşük performans gösteren normal ifadelerin oluşturulması şaşırtıcı derecede kolaydır. Bazı durumlarda, aşırı geri izlemeyi kullanan normal ifade işlemleri, normal ifade düzeniyle neredeyse eşleşen metinleri işlerken yanıt vermeyi durduruyor gibi görünebilir. .NET Normal İfade altyapısı hakkında daha fazla bilgi için bkz . Normal ifade davranışının ayrıntıları. Aşırı geri izleme hakkında daha fazla bilgi için bkz . Geri izleme.

.NET Framework 4.5'den başlayarak, aşırı geri izlemeyi sınırlamak için normal ifade eşleşmeleri için bir zaman aşımı aralığı tanımlayabilirsiniz. Normal ifade düzenine ve giriş metnine bağlı olarak, yürütme süresi belirtilen zaman aşımı aralığını aşabilir, ancak belirtilen zaman aşımı aralığından daha fazla geri izleme harcamaz. Normal ifade altyapısı zaman aşımına uğradıysa bir RegexMatchTimeoutException özel durum oluşturur. Çoğu durumda bu, normal ifade düzeniyle neredeyse eşleşen metinleri eşleştirmeye çalışarak normal ifade altyapısının işlem gücünü boşa harcamasını önler. Ancak zaman aşımı aralığının çok düşük olduğunu veya geçerli makine yükünün performansta genel bir düşüşe neden olduğunu da gösterebilir.

Özel durumun nasıl işleneceğiniz, özel durumun nedenlerine bağlıdır. Zaman aşımı aralığı çok düşük ayarlandığından veya aşırı makine yükünden dolayı özel durum oluşursa, zaman aşımı aralığını artırabilir ve eşleşen işlemi yeniden deneyebilirsiniz. Normal ifade aşırı geri izlemeyi gerektirdiğinden özel durum oluşursa, bir eşleşme olmadığını varsayabilir ve isteğe bağlı olarak, normal ifade desenini değiştirmenize yardımcı olacak bilgileri günlüğe kaydedebilirsiniz.

Normal ifade nesnesinin örneğini oluştururken oluşturucuyu Regex(String, RegexOptions, TimeSpan) çağırarak zaman aşımı aralığı ayarlayabilirsiniz. Statik yöntemler için, parametresi olan matchTimeout eşleşen bir yöntemin aşırı yüklemesini çağırarak zaman aşımı aralığı ayarlayabilirsiniz. Zaman aşımı değerini açıkça ayarlamazsanız, varsayılan zaman aşımı değeri aşağıdaki gibi belirlenir:

  • Varsa, uygulama genelinde zaman aşımı değerini kullanarak. Bir değerin dize gösterimini TimeSpan özelliğine atamak için yöntemini çağırarak AppDomain.SetData uygulama genelinde zaman aşımı değerini REGEX_DEFAULT_MATCH_TIMEOUT ayarlayın.
  • uygulama genelinde zaman aşımı değeri InfiniteMatchTimeoutayarlanmamışsa değerini kullanarak.

Önemli

Tüm normal ifade desen eşleştirme işlemlerinde bir zaman aşımı değeri ayarlamanızı öneririz. Daha fazla bilgi için bkz . Normal ifadeler için en iyi yöntemler.

Örnekler

Aşağıdaki örnek, bir dizedeki sözcüklerin tekrar tekrar tekrar olup olmadığını denetlemek için normal bir ifade kullanır. Normal ifade \b(?<word>\w+)\s+(\k<word>)\b aşağıdaki tabloda gösterildiği gibi yorumlanabilir.

Desen Açıklama
\b Eşleşmeyi bir sözcük sınırından başlatın.
(?<word>\w+) Bir veya daha fazla sözcük karakterini bir sözcük sınırına kadar eşleştirin. Yakalanan bu gruba adını verin word.
\s+ Bir veya daha fazla boşluk karakteri eşleştirin.
(\k<word>) adlı wordyakalanan grubu eşleştirin.
\b Bir sözcük sınırıyla eşleş.
using System;
using System.Text.RegularExpressions;

public class Test
{
    public static void Main ()
    {
        // Define a regular expression for repeated words.
        Regex rx = new Regex(@"\b(?<word>\w+)\s+(\k<word>)\b",
          RegexOptions.Compiled | RegexOptions.IgnoreCase);

        // Define a test string.
        string text = "The the quick brown fox  fox jumps over the lazy dog dog.";

        // Find matches.
        MatchCollection matches = rx.Matches(text);

        // Report the number of matches found.
        Console.WriteLine("{0} matches found in:\n   {1}",
                          matches.Count,
                          text);

        // Report on each match.
        foreach (Match match in matches)
        {
            GroupCollection groups = match.Groups;
            Console.WriteLine("'{0}' repeated at positions {1} and {2}",
                              groups["word"].Value,
                              groups[0].Index,
                              groups[1].Index);
        }
    }
}

// The example produces the following output to the console:
//       3 matches found in:
//          The the quick brown fox  fox jumps over the lazy dog dog.
//       'The' repeated at positions 0 and 4
//       'fox' repeated at positions 20 and 25
//       'dog' repeated at positions 49 and 53
Imports System.Text.RegularExpressions

Public Module Test

    Public Sub Main()
        ' Define a regular expression for repeated words.
        Dim rx As New Regex("\b(?<word>\w+)\s+(\k<word>)\b", _
               RegexOptions.Compiled Or RegexOptions.IgnoreCase)

        ' Define a test string.        
        Dim text As String = "The the quick brown fox  fox jumps over the lazy dog dog."
        
        ' Find matches.
        Dim matches As MatchCollection = rx.Matches(text)

        ' Report the number of matches found.
        Console.WriteLine("{0} matches found in:", matches.Count)
        Console.WriteLine("   {0}", text)

        ' Report on each match.
        For Each match As Match In matches
            Dim groups As GroupCollection = match.Groups
            Console.WriteLine("'{0}' repeated at positions {1} and {2}", _ 
                              groups.Item("word").Value, _
                              groups.Item(0).Index, _
                              groups.Item(1).Index)
        Next
    End Sub
End Module
' The example produces the following output to the console:
'       3 matches found in:
'          The the quick brown fox  fox jumps over the lazy dog dog.
'       'The' repeated at positions 0 and 4
'       'fox' repeated at positions 20 and 25
'       'dog' repeated at positions 49 and 53

Sonraki örnek, bir dizenin para birimi değerini temsil edip etmediğini veya para birimi değerini temsil etmek için doğru biçime sahip olup olmadığını denetlemek için normal ifadenin kullanımını gösterir. Bu durumda, normal ifade, en-US kültürünün NumberFormatInfo.CurrencyDecimalSeparator, CurrencyDecimalDigits, NumberFormatInfo.CurrencySymbol, NumberFormatInfo.NegativeSignve NumberFormatInfo.PositiveSign özelliklerinden dinamik olarak oluşturulur. Sonuçta elde edilen normal ifade şeklindedir ^\s*[\+-]?\s?\$?\s?(\d*\.?\d{2}?){1}$. Bu normal ifade aşağıdaki tabloda gösterildiği gibi yorumlanabilir.

Desen Açıklama
^ Dizenin başlangıcından başlayın.
\s* Sıfır veya daha fazla boşluk karakteriyle eşleş.
[\+-]? Pozitif işaretin veya negatif işaretin sıfır veya bir oluşumunu eşleştirin.
\s? Sıfır veya bir beyaz boşluk karakterini eşleştirin.
\$? Dolar işaretinin sıfırını veya bir oluşumunu eşleştirin.
\s? Sıfır veya bir beyaz boşluk karakterini eşleştirin.
\d* Sıfır veya daha fazla ondalık basamağı eşleştirin.
\.? Sıfır veya bir ondalık nokta simgesiyle eşleş.
(\d{2})? 1. grubu yakalama: İki ondalık basamağı sıfır veya bir kez eşleştirin.
(\d*\.?(\d{2})?){1} En az bir kez ondalık nokta simgesiyle ayrılmış tamsayı ve kesirli basamak desenini eşleştirin.
$ Dizenin sonunu eşleştirin.

Bu durumda normal ifade, geçerli bir para birimi dizesinin grup ayırıcı simgeleri içermediğini ve kesirli basamak içermediğini veya belirtilen kültürün CurrencyDecimalDigits özelliği tarafından tanımlanan kesirli basamak sayısını içerdiğini varsayar.

using System;
using System.Globalization;
using System.Text.RegularExpressions;

public class Example
{
    public static void Main()
    {
        // Get the en-US NumberFormatInfo object to build the regular 
        // expression pattern dynamically.
        NumberFormatInfo nfi = CultureInfo.GetCultureInfo("en-US").NumberFormat;

        // Define the regular expression pattern.
        string pattern;
        pattern = @"^\s*[";
        // Get the positive and negative sign symbols.
        pattern += Regex.Escape(nfi.PositiveSign + nfi.NegativeSign) + @"]?\s?";
        // Get the currency symbol.
        pattern += Regex.Escape(nfi.CurrencySymbol) + @"?\s?";
        // Add integral digits to the pattern.
        pattern += @"(\d*";
        // Add the decimal separator.
        pattern += Regex.Escape(nfi.CurrencyDecimalSeparator) + "?";
        // Add the fractional digits.
        pattern += @"(\d{";
        // Determine the number of fractional digits in currency values.
        pattern += nfi.CurrencyDecimalDigits.ToString() + "})?){1}$";

        Console.WriteLine($"Pattern is {pattern}\n");

        Regex rgx = new Regex(pattern);

        // Define some test strings.
        string[] tests = { "-42", "19.99", "0.001", "100 USD",
                         ".34", "0.34", "1,052.21", "$10.62",
                         "+1.43", "-$0.23" };

        // Check each test string against the regular expression.
        foreach (string test in tests)
        {
            if (rgx.IsMatch(test))
                Console.WriteLine($"{test} is a currency value.");
            else
                Console.WriteLine($"{test} is not a currency value.");
        }
    }
}
// The example displays the following output:
//       Pattern is ^\s*[\+-]?\s?\$?\s?(\d*\.?(\d{2})?){1}$
//
//       -42 is a currency value.
//       19.99 is a currency value.
//       0.001 is not a currency value.
//       100 USD is not a currency value.
//       .34 is a currency value.
//       0.34 is a currency value.
//       1,052.21 is not a currency value.
//       $10.62 is a currency value.
//       +1.43 is a currency value.
//       -$0.23 is a currency value.
Imports System.Globalization
Imports System.Text.RegularExpressions

Public Module Example
   Public Sub Main()
      ' Get the current NumberFormatInfo object to build the regular 
      ' expression pattern dynamically.
      Dim nfi As NumberFormatInfo = CultureInfo.GetCultureInfo("en-US").NumberFormat

      ' Define the regular expression pattern.
      Dim pattern As String 
      pattern = "^\s*["
      ' Get the positive and negative sign symbols.
      pattern += Regex.Escape(nfi.PositiveSign + nfi.NegativeSign) + "]?\s?"
      ' Get the currency symbol.
      pattern += Regex.Escape(nfi.CurrencySymbol) + "?\s?"
      ' Add integral digits to the pattern.
      pattern += "(\d*"
      ' Add the decimal separator.
      pattern += Regex.Escape(nfi.CurrencyDecimalSeparator) + "?"
      ' Add the fractional digits.
      pattern += "(\d{"
      ' Determine the number of fractional digits in currency values.
      pattern += nfi.CurrencyDecimalDigits.ToString() + "})?){1}$"
      
      Console.WriteLine("Pattern is {0}", pattern)
      Console.WriteLine()
      
      Dim rgx As New Regex(pattern)

      ' Define some test strings.
      Dim tests() As String = {"-42", "19.99", "0.001", "100 USD", _
                               ".34", "0.34", "1,052.21", "$10.62", _
                               "+1.43", "-$0.23" }

      ' Check each test string against the regular expression.
      For Each test As String In tests
         If rgx.IsMatch(test) Then
            Console.WriteLine("{0} is a currency value.", test)
         Else
            Console.WriteLine("{0} is not a currency value.", test)
         End If
      Next
   End Sub
End Module
' The example displays the following output:
'       Pattern is ^\s*[\+-]?\s?\$?\s?(\d*\.?(\d{2})?){1}$
'
'       -42 is a currency value.
'       19.99 is a currency value.
'       0.001 is not a currency value.
'       100 USD is not a currency value.
'       .34 is a currency value.
'       0.34 is a currency value.
'       1,052.21 is not a currency value.
'       $10.62 is a currency value.
'       +1.43 is a currency value.
'       -$0.23 is a currency value.

Bu örnekteki normal ifade dinamik olarak oluşturulduğundan, belirtilen kültürün para birimi simgesinin, ondalık işaretinin veya pozitif ve negatif işaretlerinin (bu örnekte en-US) normal ifade altyapısı tarafından normal ifade dili işleçleri olarak yanlış yorumlanıp yorumlanamayacağını tasarım zamanında bilmezsiniz. Herhangi bir yanlış yorumlamayı önlemek için örnek, dinamik olarak oluşturulan her dizeyi yöntemine Escape geçirir.