C# 中的正则表达式如何仅替换捕获组而不替换非捕获组
Regex in C# How to replace only capture groups and not non-capture groups
我正在使用 C# 在 Visual Studios 2013 Express 中编写正则表达式。我试图在包含单词和 !@#$%^&*()_- 的每个字符串周围加上单引号,除了:
- 和
- 或
- 没有
- 空()
- notempty()
- 当前日期()
- 任何已经用单引号引起来的字符串。
这是我的正则表达式及其作用的示例:
https://regex101.com/r/nI1qP0/1
我只想在捕获组两边加上单引号,而让非捕获组保持不变。我知道这可以通过环顾四周来完成,但我不知道怎么做。
您可以使用这个正则表达式:
(?:'[^']*'|(?:\b(?:(?:not)?empty|currentdate)\(\)|and|or|not))|([!@#$%^&*_.\w-]+)
此处忽略的匹配项不会被捕获,可以使用 Match.Groups[1]
检索要引用的词。然后,您可以在 Match.Groups[1]
周围添加引号,并根据需要替换整个输入。
您需要使用匹配评估器或回调方法。关键是你可以在这个方法中检查匹配和捕获的组,并根据你的模式决定采取什么行动。
所以,添加这个回调方法(如果调用方法是非静态的,则可能是非静态的):
public static string repl(Match m)
{
return !string.IsNullOrEmpty(m.Groups[1].Value) ?
m.Value.Replace(m.Groups[1].Value, string.Format("'{0}'", m.Groups[1].Value)) :
m.Value;
}
然后,使用 overload of Regex.Replace
with the match evaluator (=callback method):
var s = "'This is not captured' but this is and not or empty() notempty() currentdate() capture";
var rx = new Regex(@"(?:'[^']*'|(?:\b(?:(?:not)?empty|currentdate)\(\)|and|or|not))|([!@#$%^&*_.\w-]+)");
Console.WriteLine(rx.Replace(s, repl));
请注意,您可以使用 lambda 表达式缩短代码:
Console.WriteLine(rx.Replace(s, m => !string.IsNullOrEmpty(m.Groups[1].Value) ?
m.Value.Replace(m.Groups[1].Value, string.Format("'{0}'", m.Groups[1].Value)) :
m.Value));
我没有试图忽略其中包含单词 and!@#$%^&*()_- 的字符串,而是将它们包含在我的搜索中,在两端放置一个额外的单引号,然后删除两个单引号的所有实例如下:
// Find any string of words and !@#$%^&*()_- in and out of quotes.
Regex getwords = new Regex(@"(^(?!and\b)(?!or\b)(?!not\b)(?!empty\b)(?!notempty\b)(?!currentdate\b)([\w!@#$%^&*())_-]+)|((?!and\b)(?!or\b)(?!not\b)(?!empty\b)(?!notempty\b)(?!currentdate\b)(?<=\W)([\w!@#$%^&*()_-]+)|('[\w\s!@#$%^&*()_-]+')))", RegexOptions.IgnoreCase);
// Find all cases of two single quotes
Regex getQuotes = new Regex(@"('')");
// Get string from user
Console.WriteLine("Type in a string");
string search = Console.ReadLine();
// Execute Expressions.
search = getwords.Replace(search, "''");
search = getQuotes.Replace(search, "'");
我正在使用 C# 在 Visual Studios 2013 Express 中编写正则表达式。我试图在包含单词和 !@#$%^&*()_- 的每个字符串周围加上单引号,除了:
- 和
- 或
- 没有
- 空()
- notempty()
- 当前日期()
- 任何已经用单引号引起来的字符串。
这是我的正则表达式及其作用的示例: https://regex101.com/r/nI1qP0/1
我只想在捕获组两边加上单引号,而让非捕获组保持不变。我知道这可以通过环顾四周来完成,但我不知道怎么做。
您可以使用这个正则表达式:
(?:'[^']*'|(?:\b(?:(?:not)?empty|currentdate)\(\)|and|or|not))|([!@#$%^&*_.\w-]+)
此处忽略的匹配项不会被捕获,可以使用 Match.Groups[1]
检索要引用的词。然后,您可以在 Match.Groups[1]
周围添加引号,并根据需要替换整个输入。
您需要使用匹配评估器或回调方法。关键是你可以在这个方法中检查匹配和捕获的组,并根据你的模式决定采取什么行动。
所以,添加这个回调方法(如果调用方法是非静态的,则可能是非静态的):
public static string repl(Match m)
{
return !string.IsNullOrEmpty(m.Groups[1].Value) ?
m.Value.Replace(m.Groups[1].Value, string.Format("'{0}'", m.Groups[1].Value)) :
m.Value;
}
然后,使用 overload of Regex.Replace
with the match evaluator (=callback method):
var s = "'This is not captured' but this is and not or empty() notempty() currentdate() capture";
var rx = new Regex(@"(?:'[^']*'|(?:\b(?:(?:not)?empty|currentdate)\(\)|and|or|not))|([!@#$%^&*_.\w-]+)");
Console.WriteLine(rx.Replace(s, repl));
请注意,您可以使用 lambda 表达式缩短代码:
Console.WriteLine(rx.Replace(s, m => !string.IsNullOrEmpty(m.Groups[1].Value) ?
m.Value.Replace(m.Groups[1].Value, string.Format("'{0}'", m.Groups[1].Value)) :
m.Value));
我没有试图忽略其中包含单词 and!@#$%^&*()_- 的字符串,而是将它们包含在我的搜索中,在两端放置一个额外的单引号,然后删除两个单引号的所有实例如下:
// Find any string of words and !@#$%^&*()_- in and out of quotes.
Regex getwords = new Regex(@"(^(?!and\b)(?!or\b)(?!not\b)(?!empty\b)(?!notempty\b)(?!currentdate\b)([\w!@#$%^&*())_-]+)|((?!and\b)(?!or\b)(?!not\b)(?!empty\b)(?!notempty\b)(?!currentdate\b)(?<=\W)([\w!@#$%^&*()_-]+)|('[\w\s!@#$%^&*()_-]+')))", RegexOptions.IgnoreCase);
// Find all cases of two single quotes
Regex getQuotes = new Regex(@"('')");
// Get string from user
Console.WriteLine("Type in a string");
string search = Console.ReadLine();
// Execute Expressions.
search = getwords.Replace(search, "''");
search = getQuotes.Replace(search, "'");