正则表达式提取文本的日期

本文地址:http://www.cnblogs.com/vnii/archive/2012/11/22/2782865.html

接到需求,将数据库里面的一些标题数据中含有日期的给提取出来,利用提取的时间和当前时间来计算时间间隔,本像利用sql 的patindex等函数来提取,发现sql来写比较繁琐,后用正则表达式结合C#实现,本文主要记录正则表达式部分 (必需有年,且格式顺序为年月日,中间分隔符为[".","年","-","/"],月份和日可以为1月1日,01月01日)

先上表达式结果:

(?<Date>((?<!\d)((\d{2,4}(\.|年|\/|\-))((((0?[13578]|1[02])(\.|月|\/|\-))((3[01])|([12][0-9])|(0?[1-9])))|(0?2(\.|月|\/|\-)((2[0-8])|(1[0-9])|(0?[1-9])))|(((0?[469]|11)(\.|月|\/|\-))((30)|([12][0-9])|(0?[1-9]))))|((([0-9]{2})((0[48]|[2468][048]|[13579][26])|((0[48]|[2468][048]|[3579][26])00))(\.|年|\/|\-))0?2(\.|月|\/|\-)29))日?(?!\d)) 

1.写这个正则的目的主要是为了从数据的标题中获取包含的日期

2.对应格式为 年月日(yyyy年MM月dd日、yyyy年M月d日、yyyy.MM.dd、yyyy.M.d、yyyy/MM/dd、yyyy/M/d、yyyy-MM-dd、yyyy-M-d) ,支持闰年(闰年参考了http://www.cnblogs.com/jay-xu33/archive/2009/01/08/1371953.html)

3.代码中的 (?<!\d)和(?!\d)注意用法,其中 (?<!\d)为反向否定预查,(?!\d)为正向否定预查 可见 http://baike.baidu.com/view/94238.htm 

4.闰年部分

(
  (
      ([0-9]{2})((0[48]|[2468][048]|[13579][26])  //被4整除,不被100整除
      |
      ((0[48]|[2468][048]|[3579][26])00)  //被400整除
  )
  (\.|年|\/|\-)
)
0?2(\.|月|\/|\-)29) //2月29 02月29


//将闰年的两个条件合并结合如下
((([0-9]{2})((0[48]|[2468][048]|[13579][26])|((0[48]|[2468][048]|[3579][26])00))(\.|年|\/|\-))0?2(\.|月|\/|\-)29)

5.非闰年部分

(
    (
        ((0?[13578]|1[02])(\.|月|\/|\-))  //月份 1,3,5,7,8,10,12
        ((3[01])|([12][0-9])|(0?[1-9]))  //月份 1,3,5,7,8,10,12 对应的日期,包含31日
    )
    |
        (0?2(\.|月|\/|\-)((2[0-8])|(1[0-9])|(0?[1-9])))  //非闰年2月份 只包括28日
    |
    (
        ((0?[469]|11)(\.|月|\/|\-))  //月份 4,6,9,11
        ((30)|([12][0-9])|(0?[1-9]))  //月份 4,6,9,11 对应的日期,包含31日

    )
)


将大月、小月和2月合并如下:
((((0?[13578]|1[02])(\.|月|\/|\-))((3[01])|([12][0-9])|(0?[1-9])))|(0?2(\.|月|\/|\-)((2[0-8])|(1[0-9])|(0?[1-9])))|(((0?[469]|11)(\.|月|\/|\-))((30)|([12][0-9])|(0?[1-9]))))

6.合并闰年和非闰年

7.利用 (?<!\d)和(?!\d)和来判断日期的首尾的开始和结束

忧郁的匹格 2012.11.22 发布于博客园 http://www.cnblogs.com/vnii

posted on 2012-11-22 16:26  忧郁的匹格  阅读(11825)  评论(0编辑  收藏  举报