Recipe10.6.Augmenting the Basic String Replacement Function


Recipe 10.6. Augmenting the Basic String Replacement Function

Problem

You need to replace character patterns within the target string with a new string. However, in this case, each replacement operation has a unique set of conditions that must be satisfied in order to allow the replacement to occur. Consider, for example, that you receive a string containing information and you need to make global modifications that will depend on a specific criterion.

Solution

Use the overloaded instance Replace method shown in Example 10-7 that accepts a MatchEvaluator delegate along with its other parameters. The MatchEvaluator delegate is a callback method that overrides the default behavior of the Replace method.

Example 10-7. Overloaded Replace method that accepts a MatchEvaluator delegate

 using System; using System.Text.RegularExpressions; public static string MatchHandler(Match theMatch) {     // Handle all ControlID_ entries.     if (theMatch.Value.StartsWith("ControlID_"))     {         long controlValue = 0;         // Obtain the numeric value of the Top attribute.         Match topAttribiteMatch = Regex.Match(theMatch.Value, "Top=([-]*\\d*)");         if (topAttribiteMatch.Success)         {             if (topAttribiteMatch.Groups[1].Value.Trim().Equals(""))             {                 // If blank, set to zero.                 return (theMatch.Value.Replace(                         topAttribiteMatch.Groups[0].Value.Trim(),                         "Top=0"));             }             else if (topAttribiteMatch.Groups[1].Value.Trim().StartsWith("-"))             {                 // If only a negative sign (syntax error), set to zero.                 return (theMatch.Value.Replace(                         topAttribiteMatch.Groups[0].Value.Trim(), "Top=0"));             }             else             {                 // We have a valid number.                 // Convert the matched string to a numeric value.                 controlValue = long.Parse(topAttribiteMatch.Groups[1].Value,                             System.Globalization.NumberStyles.Any);                 // If the Top attribute is out of the specified range,                 // set it to zero.                 if (controlValue < 0 || controlValue > 5000)                 {                     return (theMatch.Value.Replace(                             topAttribiteMatch.Groups[0].Value.Trim(),                             "Top=0"));                 }             }         }     } } 

The callback method for the Replace method is shown here:

 public static void ComplexReplace(string matchPattern, string source) {     MatchEvaluator replaceCallback = new MatchEvaluator(MatchHandler);     Regex RE = new Regex(matchPattern, RegexOptions.Multiline);     string newString = RE.Replace(source, replaceCallback);     Console.WriteLine("Replaced String = " + newString); } 

To use this callback method with the static Replace method, modify the previous ComplexReplace method as follows:

 public void ComplexReplace(string matchPattern, string source) {     MatchEvaluator replaceCallback = new MatchEvaluator(MatchHandler);      string newString = Regex.Replace(source, matchPattern,                                       replaceCallback);     Console.WriteLine("Replaced String = " + newString); } 

where source is the original string to run the replace operation against, and matchPattern is the regular expression pattern to match in the source string.

If the ComplexReplace method is called from the following code:

 public static void TestComplexReplace( ) {     string matchPattern = "(ControlID_.*)";     string source = @"WindowID=Main     ControlID_TextBox1 Top=-100 Left=0 Text=BLANK     ControlID_Label1 Top=9999990 Left=0 Caption=Enter Name Here     ControlID_Label2 Top= Left=0 Caption=Enter Name Here";     ComplexReplace(matchPattern, source); } 

only the Top attributes of the ControlID_* lines are changed from their original values to 0.

The result of this replace action will change the Top attribute value of a ControlID_* line to zero if it is less than zero or greater than 5000. Any other tag that contains a Top attribute will remain unchanged. The following three lines of the source string will be changed from:

 ControlID_TextBox1 Top=-100 Left=0 Text=BLANK ControlID_Label1 Top=9999990 Left=0 Caption=Enter Name Here ControlID_Label2 Top= Left=0 Caption=Enter Name Here"; 

to:

 ControlID_TextBox1 Top=0 Left=0 Text=BLANK ControlID_Label1 Top=0 Left=0 Caption=Enter Name Here ControlID_Label2 Top=0 Left=0 Caption=Enter Name Here"; 

Discussion

The MatchEvaluator delegate, which is automatically invoked when it is supplied as a parameter to the Regex class's Replace method, allows for custom replacement of each string that conforms to the regular expression pattern.

If the current Match object is operating on a ControlID_* line with a Top attribute that is out of the specified range, the code within the MatchHandler callback method returns a new modified string. Otherwise, the currently matched string is returned unchanged. This ability allows you to override the default Replace functionality by replacing only that part of the source string that meets certain criteria. The code within this callback method gives you some idea of what can be accomplished using this replacement technique.

To make use of this callback method, you need a way to call it from the ComplexReplace method. First, a variable of type System.Text.RegularExpressions. MatchEvaluator is created. This variable (replaceCallback) is the delegate that is used to call the MatchHandler method:

 MatchEvaluator replaceCallback = new MatchEvaluator(MatchHandler); 

Finally, the Replace method is called with the reference to the MatchEvaluator delegate passed in as a parameter:

 string newString = RE.Replace(source, replaceCallback); 

See Also

See the ".NET Framework Regular Expressions" topic in the MSDN documentation.



C# Cookbook
Secure Programming Cookbook for C and C++: Recipes for Cryptography, Authentication, Input Validation & More
ISBN: 0596003943
EAN: 2147483647
Year: 2004
Pages: 424

flylib.com © 2008-2017.
If you may any questions please contact us: flylib@qtcs.net