Pattern matching and placeholder values
Easiest would be to replace each %Label%
with (?<Label>.*?)
, and escape any other characters.
%Artist%-%Album%-%Track%-%Title%.mp3
becomes
(?<Artist>.*?)-(?<Album>.*?)-(?<Track>.*?)-(?<Title>.*?)\.mp3
You would then get each component into named capture groups.
Dictinary<string,string> match_filename(string rule, string filename) {
Regex tag_re = new Regex(@'%(\w+)%');
string pattern = tag_re.Replace(Regex.escape(rule), @'(?<$1>.*?)');
Regex filename_re = new Regex(pattern);
Match match = filename_re.Match(filename);
Dictionary<string,string> tokens =
new Dictionary<string,string>();
for (int counter = 1; counter < match.Groups.Count; counter++)
{
string group_name = filename_re.GroupNameFromNumber(counter);
tokens.Add(group_name, m.Groups[counter].Value);
}
return tokens;
}
But if the user leaves out the delimiters, or if the delimiters could be contained within the fields, you could get some strange results. The pattern would for %Artist%%Album%
would become (?<Artist>.*?)(?<Album>.*?)
which is equivalent to .*?.*?
. The pattern wouldn't know where to split.
This could be solved if you know the format of certain fields, such as the track-number. If you translate %Track%
to (?<Track>\d+)
instead, the pattern would know that any digits in the filename must be the Track
.