I've come up with what seems to be a simple, and extensible solution. I just create a list of much simpler regular expressions, one for each of the possible arguments. I then iterate through that list, and if I get a match for a particular argument, I remove the match from the target string. This ensures that each argument is only in the command string once, and it doesn't matter where in the string it is found (any order - sorted). At the end, if there is anything left in the command string, then it had an invalid argument.
So , for the simple case as mentioned in the comments above, I would create a list with:
List<string> list = new List<string>() {
@"$\s*process",
@"\s+(upper|lower)case",
@"\s+remove\s+(punctuation|whitespace|numbers)
};
And the code to validate is
StringBuilder sb = new StringBuilder(command);
foreach (string regexp in list) {
Match m = Regex.Match(sb.ToString(), regexp,
RegexOptions.IgnoreCase|RegexOptions.ExplicitCapture);
if (m.Success)
sb.Remove(m.Index, m.Length);
}
return string.IsNullOrWhiteSpace(sb.ToString());