Replace Only Some Groups with Regex

Replace only some groups with Regex

A good idea could be to encapsulate everything inside groups, no matter if need to identify them or not. That way you can use them in your replacement string. For example:

var pattern = @"(-)(\d+)(-)";
var replaced = Regex.Replace(text, pattern, "$1AA$3");

or using a MatchEvaluator:

var replaced = Regex.Replace(text, pattern, m => m.Groups[1].Value + "AA" + m.Groups[3].Value);

Another way, slightly messy, could be using a lookbehind/lookahead:

(?<=-)(\d+)(?=-)

How to replace different matching groups with different text in Regex

Here is a regular expression that would work for you. But it's a kind of trick that only works because this substitution is part of the match.

Regular expression

(n)ounC2|(v)erbC1|(adj)ectiveB1

Substitution

 ($1$2$3)

Use (\1\2\3) instead if you're using Python

Explanation

(n)ounC2|(v)erbC1|(adj)ectiveB1 will match either nounC2, verbC1 or adjectiveB1

When it matches nounC2, Group 1 will contain n, Group 2 and 3 contain nothing

When it matches verbC1, Group 2 will contain v, Group 1 and 3 contain nothing

When it matches adjectiveB1, Group 3 will contain adj, Group 1 and 2 contain nothing

Every match is replaced with a space followed by the values of the 3 groups between parenthesis.

Demos

Demo on RegEx101

Code snippet (JavaScript)

const regex = /(n)ounC2|(v)erbC1|(adj)ectiveB1/gm;const str = `dangernounC2cautionnounC2alertverbC1dangerousadjectiveB1eatverbC1prettyadjectiveB1`;const subst = ` ($1$2$3)`;
// The substituted value will be contained in the result variableconst result = str.replace(regex, subst);
console.log('Substitution result: ', result);

Regex in C# How to replace only capture groups and not non-capture groups

Instead of trying to ignore the strings with words and!@#$%^&*()_- in them, I just included them in my search, placed an extra single quote on either end, and then remove all instances of two single quotes like so:

 // 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, "'$1'");
search = getQuotes.Replace(search, "'");

Regex replace only matching groups and ignore non-matching groups?

Turn the first and last non-capturing groups to capturing groups so that you could refer thoses chars in the replacement part and remove the unnecessary second capturing group.

string w_name = "0x010102_default_prg_L2_E2_LDep1_LLC";
string regex_exp = @"(E\d)[\w\d_]+(_LLC)";
w_name = Regex.Replace(w_name, regex_exp, "$1$2");

DEMO

or

string regex_exp = @"(?<=E\d)[\w\d_]+(?=_LLC)";
w_name = Regex.Replace(w_name, regex_exp, string.Empty);

How to replace only specific groups in a match in R using stringr package?

You may capture what you need to keep and just match what you need to replace, use

> gsub("(#[^ \t#]+ )[^#]*(#)", "\\1REPLACED WITH THIS\\2", text)
[1] "My code #snippet REPLACED WITH THIS# is simple"

Details

  • (#[^ \t#]+ ) - Group 1: #, then any 1+ chars other than #, space and tab, and a space
  • [^#]* - 0+ chars other than #
  • (#) - Group 2: a # char

Another way: use gsubfn with a pattern where all your pattern parts are captured into separate groups and then rebuild the replacement after performing the required manipulations:

> gsubfn::gsubfn("(#[^ \t#]+ )([^#]*)(#)", function(x, y, z) paste0(x, "REPLACED WITH THIS", z), text)
[1] "My code #snippet REPLACED WITH THIS# is simple"

Here, the x, y and z refer to the groups defined in the pattern:

(#[^ \t#]+ )([^#]*)(#)
| --- x ---||- y -||z|

With stringr, you may - but you should be very careful with this - use a pattern with lookbehind/lookahead:

> stringr::str_replace_all(text, "(?<=#[^ \t#]{1,1000} )[^#]*(?=#)", "REPLACED WITH THIS")
[1] "My code #snippet REPLACED WITH THIS# is simple"

The (?<=#[^ \t#]{1,1000} ) lookbehind works because it matches a known length pattern (the {1,1000} says there can be from 1 to 1000 occurrences of any chars but space, tab and #), and this "constrained-width lookbehind" is supported since stringr uses ICU regex library.

How to replace a matched group value with Regex

If you insist Regex replacing, please note C# cannot modify a built string, you need to get a new string with the needed part replaced.

var connectionString = @"data source=MY-PC\SQLEXPRESS;";
var pattern = @"(data source=)((\w|\-)+?\\\w+?)\;";
var newConnectionString = Regex.Replace(connectionString, pattern, "$1" + "something");
Console.WriteLine(newConnectionString);

R - Replace Group 1 match in regex but not full match

It is not the way regex was designed. Capturing is a mechanism to get the parts of strings you need and when replacing, it is used to keep parts of matches, not to discard.

Thus, a natural solution is to wrap what you need to keep with capturing groups.

In this case here, use

str_replace_all("abc", "(a)[a-z](c)", "\\1z\\2")

Or with lookarounds (if the lookbehind is a fixed/known width pattern):

str_replace_all("abc", "(?<=a)[a-z](?=c)", "z")

Replace only a part of matched regular expression in c#

Change your code to,

string input = "hello everyone, hullo anything";
string pattern = "(h.llo )[A-Za-z]+";
string output = Regex.Replace(input,pattern,"$1world");

[A-z] matches not only A-Z, a-z but also some other extra characters.

or

string pattern = "(?<=h.llo )[A-Za-z]+";
string output = Regex.Replace(input,pattern,"world");

(?<=h.llo ) positive lookbehind asserion which asserts that the match must be preceded by h, any char, llo , space. Assertions won't match any single character but asserts whether a match is possible or not.

DEMO

Regex in C# - how I replace only one specific group in Match?

This should do it:

string Matcher(Match m)
{
if (m.Groups.Count < 3)
{
return m.Value;
}

return string.Join("", m.Groups
.OfType<Group>() //for LINQ
.Select((g, i) => i == 2 ? "replacedText" : g.Value)
.Skip(1) //for Groups[0]
.ToArray());
}

Example: http://rextester.com/DLGVPA38953

EDIT: Although the above is the answer to your question as written, you may find zero-width lookarounds simpler for your actual scenario:

Regex.Replace(input, @"(?<=e)l+(?=o)", replacement)

Example: http://rextester.com/SOWWS24307

Regex replace only groups

The problem is the \\{ in the replacement string. { doesn't need to be escaped in the replacement, only in a regular expression. And the documentation says:

If a \ in insert is followed by anything other than a digit, &, \, or $, then the \ by itself is treated as \0.

So each \\{ gets replaced with the entire match.

The correct call is

(regexp-replace #px"\\((.*)\\)\\/\\((.*)\\)"
"(A + B)/(C)"
"\\\\dfrac{\\1}{\\2}")

See DEMO



Related Topics



Leave a reply



Submit