如何通过不重写相同的捕获组来简化正则表达式?

时间:2019-03-02 07:00:58

标签: javascript regex

输入文字:

星期一至星期五:上午6:00至下午8:00

星期六至星期日:上午6:30至下午8:00

我需要匹配粗体字,以便使用以下正则表达式:

(Monday|Tuesday|Wednesday|Thursday|Friday|Saturday|Sunday) (to) (Monday|Tuesday|Wednesday|Thursday|Friday|Saturday|Sunday)

如何通过避免两次重写(Monday|Tuesday|Wednesday|Thursday|Friday|Saturday|Sunday)捕获组来简化正则表达式?

4 个答案:

答案 0 :(得分:1)

您可以定义一个字符串片段交替,然后重新使用它:

var input = "Monday to Friday 6:00 a.m. to 8:00 p.m.";
var alt = "(Monday|Tuesday|Wednesday|Thursday|Friday|Saturday|Sunday)";
var re = new RegExp("^" + alt + " (to) " + alt + ".*$");
if (re.test(input)) {
    console.log("valid");
}
else {
    console.log("invalid");
}

答案 1 :(得分:1)

如果可以做出以下假设:

  • 比赛结束后,您不需要单独捕获
  • 模式必须出现在输入的开始

那么你可以做:

^\b(( to |^)(Monday|Tuesday)){2}\b

说明

  • \b与输入的开头匹配。
  • {2}要求第一个字符为单词字符。可以防止在字符串的开头将“匹配到”。
  • ( to |^)要求主体部分连续匹配两次
  • ^在理论上可以与“ to”或输入的开头匹配,但是自从我们第一次知道我们就在开头(因为第一个\b)以来,它就与由于前一个\b无法将“与”匹配,则此操作为空操作。第二次,它不再与输入的开始匹配,因为那时我们已经匹配了一天,因此在第二次迭代中只有“ to”可以匹配。
  • Tuesdaymorning最后是为了避免类似angular.module('selectExample', []) .controller('ExampleController', ['$scope', function($scope) { $scope.newImg = ["https://picsum.photos/200", "https://picsum.photos/200/300/"] }]);的事情。

答案 2 :(得分:0)

这更短,但也更难看:

((?:(?:Mon|Tues|Wednes|Thurs|Fri|Satur|Sun)day)(?: to )?)+

尽管它也与Monday Friday之类的东西匹配(没有to)。

出于可读性考虑,我绝对会选择使用较大的版本。

答案 3 :(得分:0)

假设您的搜索文本仅包含以下格式的数据: 每天上午6:00至下午8:00,您可以使用

re.findall("([A-Za-z]*day)\s(to)\s([A-Za-z]+day)","Monday to Tuesday  6:00 a.m. to 8:00 p.m")