Выражение выражения Regex - PullRequest
       2

Выражение выражения Regex

1 голос
/ 01 сентября 2009

Может кто-нибудь поместить выражение регулярного выражения, которое будет:

  1. найти фрагмент, который начинается с [% и заканчивается%]
  2. внутри этого блока заменить все специальные символы xml на:
    & quot; & apos; & lt; & gt; & amp;
  3. оставьте все между <% =%> или <% #%> как есть, за исключением того, что убедитесь, что есть место после <% # или <% = и перед%>, например, <% = Integer.MaxValue%> должно стать <% = Integer.MaxValue%>

Источник:

[% 'test' <mtd:ddl id="asdf" runat="server"/> & <%= Integer.MaxValue% > %]

результат:

&apos;test&apos; &lt;mtd:ddl id=&quot;asdf&quot; runat=&quot;server&quot;/&gt; &amp; <%= Integer.MaxValue %>

Ответы [ 3 ]

2 голосов
/ 01 сентября 2009

Использовано 2 регулярных выражения. 1-й, чтобы соответствовать общей форме, 2-й, чтобы иметь дело с внутренней сантехникой.

Для кодирования XML я использовал малоизвестный метод, найденный в System.Security: SecurityElement.Escape Method . Я полностью уточнил это в приведенном ниже коде для акцента. Другим вариантом может быть использование метода HttpUtility.HtmlEncode , но это может включать ссылку на System.Web в зависимости от того, где вы его используете.

string[] inputs = { @"[% 'test' <mtd:ddl id=""asdf"" runat=""server""/> & <%= Integer.MaxValue %> %]",
    @"[% 'test' <mtd:ddl id=""asdf"" runat=""server""/> & <%=Integer.MaxValue %> %]",
    @"[% 'test' <mtd:ddl id=""asdf"" runat=""server""/> & <%# Integer.MaxValue%> %]",
    @"[% 'test' <mtd:ddl id=""asdf"" runat=""server""/> & <%#Integer.MaxValue%> %]",
};
string pattern = @"(?<open>\[%)(?<content>.*?)(?<close>%])";
string expressionPattern = @"(?<content>.*?)(?<tag><%(?:[=#]))\s*(?<expression>.*?)\s*%>";

foreach (string input in inputs)
{
    string result = Regex.Replace(input, pattern, m =>
        m.Groups["open"].Value +
        Regex.Replace(m.Groups["content"].Value, expressionPattern,
            expressionMatch =>
            System.Security.SecurityElement.Escape(expressionMatch.Groups["content"].Value) +
            expressionMatch.Groups["tag"].Value + " " +
            expressionMatch.Groups["expression"].Value +
            " %>"
        ) +
        m.Groups["close"].Value
    );

    Console.WriteLine("Before: {0}", input);
    Console.WriteLine("After: {0}", result);
}

Результаты:

Before: [% 'test' <mtd:ddl id="asdf" runat="server"/> & <%= Integer.MaxValue %> %]
After: [% &apos;test&apos; &lt;mtd:ddl id=&quot;asdf&quot; runat=&quot;server&quot;/&gt; &amp; <%= Integer.MaxValue %> %]
Before: [% 'test' <mtd:ddl id="asdf" runat="server"/> & <%=Integer.MaxValue %> %]
After: [% &apos;test&apos; &lt;mtd:ddl id=&quot;asdf&quot; runat=&quot;server&quot;/&gt; &amp; <%= Integer.MaxValue %> %]
Before: [% 'test' <mtd:ddl id="asdf" runat="server"/> & <%# Integer.MaxValue%> %]
After: [% &apos;test&apos; &lt;mtd:ddl id=&quot;asdf&quot; runat=&quot;server&quot;/&gt; &amp; <%# Integer.MaxValue %> %]
Before: [% 'test' <mtd:ddl id="asdf" runat="server"/> & <%#Integer.MaxValue%> %]
After: [% &apos;test&apos; &lt;mtd:ddl id=&quot;asdf&quot; runat=&quot;server&quot;/&gt; &amp; <%# Integer.MaxValue %> %]

РЕДАКТИРОВАТЬ: , если вы не хотите сохранить открытие / закрытие [%%] в конечном результате, затем измените шаблон на:

string pattern = @"\[%(?<content>.*?)%]";

Тогда обязательно удалите ссылки на m.Groups["open"].Value и m.Groups["close"].Value.

1 голос
/ 01 сентября 2009
private void button1_Click(object sender, EventArgs e)
        {
            Regex reg = new Regex(@"\[%(?<b1>.*)%\]");
            richTextBox1.Text= reg.Replace(textBox1.Text, new MatchEvaluator(f1));
        }

        static string f1(Match m)
        {
            StringBuilder sb = new StringBuilder();
            string[] a = Regex.Split(m.Groups["b1"].Value, "<%[^%>]*%>");
            MatchCollection col = Regex.Matches(m.Groups["b1"].Value, "<%[^%>]*%>");
            for (int i = 0; i < a.Length; i++)
            {
                sb.Append(a[i].Replace("&", "&amp;").Replace("'", "&apos;").Replace("\"", "&quot;").Replace("<", "&lt;").Replace(">", "&gt;"));
                if (i < col.Count)
                    sb.Append(col[i].Value);
            }
            return sb.ToString();
        }

Test1:

[% 'test' <mtd:ddl id="asdf" runat="server"/> & <%= Integer.MaxValue%> fdas<% hi%> 321%]

результат:

 &apos;test&apos; &lt;mtd:ddl id=&quot;asdf&quot; runat=&quot;server&quot;/&gt; &amp; <%= Integer.MaxValue%> fdas<% hi%> 321
0 голосов
/ 09 сентября 2009

Я думаю, что код будет понятен без использования RegEx. Я хотел бы написать отдельный метод (и модульный тест) для каждой строки вашей спецификации, а затем связать их вместе.

См. Также « Когда не использовать Regex в C # (или Java, C ++ и т. Д.)»

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...