将时间戳与描述分组

时间:2015-12-11 19:31:43

标签: javascript regex timestamp

我有使用时间表应用程序记录的任务数据。我试图解析每个任务的休息时间。

附加到任务的示例中断字符串可能如下所示:

  

1:19 pm - 10:33 pm吃tacos 10:35 pm - 11:38 pm 12:40 am - 1:24 am拿了一个   盹

我需要将其分为带有相关描述的时间戳。以上应分组如下:

  

下午1:19 - 晚上10:33吃了炸玉米饼

     

10:35 pm - 11:38 pm

     

早上12:40 - 凌晨1:24小睡了

中断间隔的描述基本上可以包含任何字符或任何长度。有些时间间隔没有描述。

我认为正则表达式是获取其描述的间隔数组的最简单方法(如果它们有一个)。

到目前为止,我有:

\d{1,2}:\d{2}[ap]m\s–\s\d{1,2}:\d{2}[ap]m

匹配时间戳1:19pm – 10:33pm10:35pm – 11:38pm12:40am – 1:24am

我使用JavaScript和match函数来解析这些数据。我想创建一个正则表达式,它将匹配时间戳及其后的所有内容,直到下一个时间戳。

我是正则表达式的初学者,所以对我很轻松。我已经在这里工作了几个小时,观看了几个视频,阅读了教程博客,并一直在试验regex101。主播,前瞻/后卫,令人困惑,我似乎无法做任何我想做的事情。不想成为编写正则表达式的专家,但我真的很想学习一些可以直接应用于我正在做的事情的新东西。

3 个答案:

答案 0 :(得分:5)

您可以使用以下正则表达式:

(\d{1,2}:\d{2}[ap]m\s*–\s*\d{1,2}:\d{2}[ap]m)(\D*(?:\d(?!\d?:\d{2}[ap]m\s)\D*)*)

请参阅regex demo

您遇到的问题是 匹配与特定模式不匹配的文字 。这可以通过淬火贪婪令牌展开循环技术来实现。后者是优选的,因为它涉及较少的回溯。我的正则表达式基于这种技术。

这是正则表达式的解释:

  • (\d{1,2}:\d{2}[ap]m\s*–\s*\d{1,2}:\d{2}[ap]m) - 匹配并捕获到第1组时间段(我只是将外部括号和*量词添加到\s类) - 因为它是你的正则表达式,我不会详细介绍
  • (\D*(?:\d(?!\d?:\d{2}[ap]m\s)\D*)*) - 这是一个展开的.*?(?=\d{1,2}:\d{2}[ap]m\s)构造,匹配任何直到第一个\d{1,2}:\d{2}[ap]m\s模式的构造。它被放置在组#2中。
    • \D* - 除数字
    • 以外的0个或多个字符
    • (?:\d(?!\d?:\d{2}[ap]m\s)\D*)* - 0个或更多个序列...
      • \d(?!\d?:\d{2}[ap]m\s) - 一个数字(\d),后跟1或0位数后跟:后跟2位数字,然后是a或{{1}然后是p,然后是一个空格
      • m - 再次,0位以外的其他字符。

JS演示:

\D*
var re = /(\d{1,2}:\d{2}[ap]m\s*–\s*\d{1,2}:\d{2}[ap]m)(\D*(?:\d(?!\d?:\d{2}[ap]m\s)\D*)*)/ig; 
var str = '1:19pm – 10:33pm ate tacos 10:35pm – 11:38pm 12:40am – 1:24am took a nap';
var m;
 
while ((m = re.exec(str)) !== null) {
    document.getElementById("r").innerHTML += "Period: " + m[1] + "<br/>";
    document.getElementById("r").innerHTML   += "Description: " + m[2] + "<br/><br/>";
}

答案 1 :(得分:4)

我确信这可以简化,但以下正则表达似乎有效:

Example Here

/(\d{1,2}:\d{2}[ap]m\s–\s\d{1,2}:\d{2}[ap]m(?:.(?!\d{1,2}:\d{2}[ap]m))*)/g

&#13;
&#13;
var input = '1:19pm – 10:33pm ate tacos 10:35pm – 11:38pm 12:40am – 1:24am took a nap';
var matches = input.match(/(\d{1,2}:\d{2}[ap]m\s–\s\d{1,2}:\d{2}[ap]m(?:.(?!\d{1,2}:\d{2}[ap]m))*)/g);

for (var i = 0; i < matches.length; i++) {
  snippet.log(matches[i]);
}
&#13;
<script src="http://tjcrowder.github.io/simple-snippets-console/snippet.js"></script>
&#13;
&#13;
&#13;

输出:

  

下午1:19 - 晚上10:33吃了炸玉米饼

     

10:35 pm - 11:38 pm

     

早上12:40 - 凌晨1:24小睡了

答案 2 :(得分:2)

希望它会有所帮助:

https://regex101.com/r/dV7vY5/1

  

(\ d {1,2}:\ d {2} [ap] m) - (\ d {1,2}:\ d {2} [ap] m)([\ s | az | AZ ] +)

输出:

  

下午1:19 - 晚上10:33吃了炸玉米饼

     

10:35 pm - 11:38 pm

     

早上12:40 - 凌晨1:24小睡了

你可以接受每一个模式:

 $1 - first hour  (1:19pm)
 $2 - second hour (10:33pm)
 $3 - string      ( ate tacos)

以下示例:

var string = '1:19pm – 10:33pm ate tacos 10:35pm – 11:38pm 12:40am – 1:24am took a nap';
var regex = /(\d{1,2}:\d{2}[ap]m) – (\d{1,2}:\d{2}[ap]m)([\s|a-z|A-Z]+)/gi;
var eachMatche = string.match(regex);

for (var i = 0; i < eachMatche.length; i++) {
  snippet.log(eachMatche[i]);
  snippet.log('period : '+ eachMatche[i].replace(regex,'$1') +' - ' + eachMatche[i].replace(regex,'$2'));
  snippet.log('description : '+eachMatche[i].replace(regex,'$3'));
}
<script src="http://tjcrowder.github.io/simple-snippets-console/snippet.js"></script>