Reputation: 49992
I need to replace some 2- and 3-digit numbers with the same number plus 10000. So
Photo.123.aspx
needs to become
Photo.10123.aspx
and also
Photo.12.aspx
needs to become
Photo.10012.aspx
I know that in .NET I can delegate the replacement to a function and just add 10000 to the number, but I'd rather stick to garden-variety RegEx if I can. Any ideas?
Upvotes: 2
Views: 3813
Reputation: 1123
Found this question since I was trying to do something similar in Vim. Ill put the solution here.
:s/Photo\.\d\+\.aspx/\=Photo\.submatch(0)+10000\.aspx/g
Upvotes: 0
Reputation: 1597
James is right that you want to use the Regex.Replace method that takes a MatchEvaluator argument. The match evaluator delegate is where you can take the numeric string you get in the match and convert it into a number that you can add 10,000 to. I used a lambda expression in place of the explicit delegate because its more compact and readable.
using System;
using System.Text.RegularExpressions;
namespace RenameAspxFile
{
sealed class Program
{
private static readonly Regex _aspxFileNameRegex = new Regex(@"(\S+\.)(\d+)(\.aspx)", RegexOptions.Compiled | RegexOptions.IgnorePatternWhitespace | RegexOptions.IgnoreCase);
private static readonly string[] _aspxFileNames= {"Photo.123.aspx", "Photo.456.aspx", "BigPhoto.789.aspx"};
static void Main(string[] args)
{
Program program = new Program();
program.Run();
}
void Run()
{
foreach (string aspxFileName in _aspxFileNames)
{
Console.WriteLine("Renamed '{0}' to '{1}'", aspxFileName, AddTenThousandToPhotoNumber(aspxFileName));
}
}
string AddTenThousandToPhotoNumber(string aspxFileName)
{
return _aspxFileNameRegex.Replace(aspxFileName, match => String.Format("{0}{1}{2}", match.Result("$1"), Int32.Parse(match.Result("$2")) + 10000, match.Result("$3")));
}
}
}
Upvotes: 6
Reputation: 416053
This will match the right part of the string, but won't tell you if it's two digits or three.
[^\d][\d]{2,3}[^\d]
Still, you could use that to grab the number, convert it to an int, add 10000, and convert that to the string you need.
Upvotes: 0
Reputation: 54894
Try the following:
"Photo\./d\.aspx" and replace with "Photo.1000$1.aspx"
"Photo\./d/d\.aspx" and replace with "Photo.100$1.aspx"
"Photo\./d/d/d\.aspx" and replace with "Photo.10$1.aspx"
That is the only way I see this happening.
Upvotes: 2
Reputation: 140923
James Curran did it little faster than me but well here is what I have for you. Think it's the smallest code you can have with Regex to do what you want.
Regex regex = new Regex(@"(\d\d\d?)", RegexOptions.None);
string result = regex.Replace(@"Photo.123.asp", delegate(Match m)
{
return "Photo.1"
+ m.Groups[1].Captures[0].Value.PadLeft(4, '0')
+ ".aspx";
}
);
Upvotes: 1
Reputation: 34120
Is there any reason it has to be VB.NET
?
s(
Photo\. (\d{2,3}) \.aspx
){
"Photo." . ($1 + 10000) . ".aspx"
}xe
Upvotes: 5
Reputation: 103545
This appears to do what you want:
static public string Evaluator(Match match)
{
return "Photo.1"
+ match.Groups[1].Captures[0].Value.PadLeft(4, '0')
+ ".aspx";
}
public void Code(params string[] args)
{
string pattern = @"Photo\.([\d]+)\.aspx";
string test = "Photo.123.aspx";
Regex regex = new Regex(pattern);
string converted = regex.Replace(test, Evaluator)
Console.WriteLine(converted);
}
Upvotes: 0
Reputation: 25427
If it's only two or three digit numbers:
(I assume you are using .NET Regex since we are talking about .aspx files)
Check for: Photo\.{\d\d\d}\.aspx
Replace with: Photo.10\1.aspx
Then check against: Photo\.{\d\d}\.aspx
Replace with: Photo.100\1.aspx
Upvotes: 1
Reputation: 63126
I think that using a RegEx for the match, and a function for the replace is most appropriate in this case, you are doing simple math, use something that is designed to do it.....
Upvotes: 6