/// <summary> /// Simple optimization. If a set is a singleton, an inverse singleton, /// or empty, it's transformed accordingly. /// </summary> private RegexNode ReduceSet() { // Extract empty-set, one and not-one case as special if (RegexCharClass.IsEmpty(Str)) { NType = Nothing; Str = null; } else if (RegexCharClass.IsSingleton(Str)) { Ch = RegexCharClass.SingletonChar(Str); Str = null; NType += (One - Set); } else if (RegexCharClass.IsSingletonInverse(Str)) { Ch = RegexCharClass.SingletonChar(Str); Str = null; NType += (Notone - Set); } return(this); }
/// <summary> /// Simple optimization. If a set is a singleton, an inverse singleton, /// or empty, it's transformed accordingly. /// </summary> internal RegexNode ReduceSet() { // Extract empty-set, one and not-one case as special if (RegexCharClass.IsEmpty(_str)) { _type = Nothing; _str = null; } else if (RegexCharClass.IsSingleton(_str)) { _ch = RegexCharClass.SingletonChar(_str); _str = null; _type += (One - Set); } else if (RegexCharClass.IsSingletonInverse(_str)) { _ch = RegexCharClass.SingletonChar(_str); _str = null; _type += (Notone - Set); } return(this); }
// !!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!! // !!!! This function must be kept synchronized with GenerateFindFirstChar !!!! // !!!! in RegexCompiler.cs !!!! // !!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!! protected override bool FindFirstChar() { int i; String set; if (0 != (runanchors & (RegexFCD.Beginning | RegexFCD.Start | RegexFCD.EndZ | RegexFCD.End))) { if (!runcode._rightToLeft) { if ((0 != (runanchors & RegexFCD.Beginning) && runtextpos > runtextbeg) || (0 != (runanchors & RegexFCD.Start) && runtextpos > runtextstart)) { runtextpos = runtextend; return(false); } if (0 != (runanchors & RegexFCD.EndZ) && runtextpos < runtextend - 1) { runtextpos = runtextend - 1; } else if (0 != (runanchors & RegexFCD.End) && runtextpos < runtextend) { runtextpos = runtextend; } } else { if ((0 != (runanchors & RegexFCD.End) && runtextpos < runtextend) || (0 != (runanchors & RegexFCD.EndZ) && (runtextpos < runtextend - 1 || (runtextpos == runtextend - 1 && CharAt(runtextpos) != '\n'))) || (0 != (runanchors & RegexFCD.Start) && runtextpos < runtextstart)) { runtextpos = runtextbeg; return(false); } if (0 != (runanchors & RegexFCD.Beginning) && runtextpos > runtextbeg) { runtextpos = runtextbeg; } } if (runbmPrefix != null) { return(runbmPrefix.IsMatch(runtext, runtextpos, runtextbeg, runtextend)); } return(true); // found a valid start or end anchor } else if (runbmPrefix != null) { runtextpos = runbmPrefix.Scan(runtext, runtextpos, runtextbeg, runtextend); if (runtextpos == -1) { runtextpos = (runcode._rightToLeft ? runtextbeg : runtextend); return(false); } return(true); } else if (runfcPrefix == null) { return(true); } runrtl = runcode._rightToLeft; runci = runfcPrefix.CaseInsensitive; set = runfcPrefix.Prefix; if (RegexCharClass.IsSingleton(set)) { char ch = RegexCharClass.SingletonChar(set); for (i = Forwardchars(); i > 0; i--) { if (ch == Forwardcharnext()) { Backwardnext(); return(true); } } } else { for (i = Forwardchars(); i > 0; i--) { if (RegexCharClass.CharInClass(Forwardcharnext(), set)) { Backwardnext(); return(true); } } } return(false); }
private void GenerateFindFirstChar() { var boyerMooreCulture = BoyerMoorePrefix != null ? Writer.DeclareField($@"private static readonly CultureInfo BoyerMooreCulture = CultureInfo.GetCultureInfo(""{BoyerMoorePrefix._culture.ToString()}"");") : null; if (!(Anchors.Beginning || Anchors.Start || Anchors.EndZ || Anchors.End) && BoyerMoorePrefix != null) { GenerateBoyerMoorePrefixScan(boyerMooreCulture); } using (Writer.Method("protected override bool FindFirstChar()")) { #if DEBUG_OUTPUT Writer.Write($@"Debug.WriteLine("""")"); Writer.Write($@"Debug.WriteLine($""Search range: from {{{runtextbeg}.ToString(CultureInfo.InvariantCulture)}} to {{{runtextend}.ToString(CultureInfo.InvariantCulture)}}"")"); Writer.Write($@"Debug.WriteLine($""Firstchar search starting at {{{runtextpos}.ToString(CultureInfo.InvariantCulture)}} stopping at {{{(IsRightToLeft ? runtextbeg : runtextend)}.ToString(CultureInfo.InvariantCulture)}}"")"); #endif if (Anchors.Beginning || Anchors.Start || Anchors.EndZ || Anchors.End) { GenerateAnchorChecks(boyerMooreCulture); } else if (BoyerMoorePrefix != null) { GenerateBoyerMoorePrefixScanCheck(); } else if (FirstCharacterPrefix == null) { Writer.Write($"return true;"); } else { var culture = DeclareCulture(); var set = FirstCharacterPrefix.GetValueOrDefault().Prefix; if (RegexCharClass.IsSingleton(set)) { var ch = RegexCharClass.SingletonChar(set); var i = Local.Parse("i"); using (Writer.For($"int {i} = {Forwardchars()}; {i} > 0; {i}--")) { using (Writer.If($"'{ch}' == {Forwardcharnext(culture)}")) { Backwardnext(); Writer.Write($"return true;"); } } } else { var i = Local.Parse("i"); using (Writer.For($"int {i} = {Forwardchars()}; i > 0; i--")) { using (Writer.If($@"{CharInClass(Forwardcharnext(culture), set)}")) { Backwardnext(); Writer.Write($"return true;"); } } } Writer.Write($"return false;"); } } }