这是我第一次使用正则表达式。我需要有一个字符串数组作为一个正则表达式模式的一部分。具体来说,我试图匹配一个日期,所以我处理的两种格式是DDTTTTMMM
和MMMDDTTTT
,月份是一个三个字母的缩写(例如:DEC
),我无法控制月份在输入中的位置。
今天的日期示例是011150DEC
或DEC011150
String[] months = {“JAN”, “FEB”, …, “DEC”}
String pattern1 = [0-9][0-9][0-9][0-9][0-9][0-9][months];
String pattern2 = [months][0-9][0-9][0-9][0-9][0-9][0-9];
例如,使用简单字符串连接:
string[] months = {"JAN", "FEB", "DEC"};
string monthsGroup = "(?:" + String.Join("|", months) + ")";
string pattern1 = @"d{6}" + monthsGroup;
string pattern2 = monthsGroup + @"d{6}";
Console.WriteLine(pattern1); // d{6}(?:JAN|FEB|DEC)
Console.WriteLine(pattern2); // (?:JAN|FEB|DEC)d{6}
当然,您也可以根据自己的喜好选择使用String.Format
或插入字符串。
正则表达式不是解析日期的好方法;想象一下闰年问题。你可以使用DateTime。TryParseExact而不是
private static bool TryMyParse(string text, out DateTime result) =>
DateTime.TryParseExact(
text,
new string[] { "ddHHmmMMM", "MMMddHHmm"},
CultureInfo.InvariantCulture,
DateTimeStyles.AssumeLocal,
out result);
演示:
string[] tests = new string[] {
"011150DEC",
"DEC011150",
"abracadabra",
};
var report = string.Join(Environment.NewLine, tests
.Select(test => $"{test,20} => {(TryMyParse(test, out var date) ? date.ToString("dd MMMM yyyy HH:mm") : "???")}"));
Console.Write(result);
输出:
011150DEC => 01 December 2022 11:50
DEC011150 => 01 December 2022 11:50
abracadabra => ???
如果你坚持使用正则表达式,让我们一步一步地构建pattern
:
// Let's use correct abbreviations instead of hardcoded ones
string months = string.Join("|", CultureInfo
.InvariantCulture
.DateTimeFormat
.AbbreviatedMonthNames
.Where(m => !string.IsNullOrEmpty(m)))
.ToUpper();
// Subpatterns for days, hours, minutes and months
string dd = "(?<dd>[0-3][0-9])"; // 00 and 39 day are still possible...
string HH = "(?<HH>[0-2][0-9])"; // 27 hour is still possible...
string mm = "(?<mm>[0-5][0-9])";
string MMM = $"(?<MMM>{months})";
// Time to construct the final pattern which should match
// either ddHHmmMMM or MMMddHHmm:
string pattern = string.Join("|",
$"(^{dd}{HH}{mm}{MMM}$)",
$"(^{MMM}{dd}{HH}{mm}$)");
看看这个怪物(然而,它让天为00
,39
允许小时为26
):
Console.Write(pattern);
输出:
(^(?<dd>[0-3][0-9])(?<HH>[0-2][0-9])(?<mm>[0-5][0-9])(?<MMM>JAN|FEB|MAR|APR|MAY|JUN|JUL|AUG|SEP|OCT|NOV|DEC)$)|(^(?<MMM>JAN|FEB|MAR|APR|MAY|JUN|JUL|AUG|SEP|OCT|NOV|DEC)(?<dd>[0-3][0-9])(?<HH>[0-2][0-9])(?<mm>[0-5][0-9])$)