【问题标题】:Extract inconsistently formatted date from string (date parsing, NLP)从字符串中提取格式不一致的日期(日期解析,NLP)
【发布时间】:2010-08-10 01:16:05
【问题描述】:

我有很多文件,其中一些文件名中嵌入了日期。日期的格式不一致且通常不完整,例如“Aug06”、“Aug2006”、“August 2006”、“08-06”、“01-08-06”、“2006”、“011004”等。除此之外,一些文件名还有一些不相关的数字,看起来有点像日期,例如“20202010”。

简而言之,日期通常不完整,有时不存在,格式不一致,并且嵌入在带有其他信息的字符串中,例如“报告 Aug06.xls”。

是否有任何可用的 Perl 模块可以很好地从这样的字符串中猜测日期?它不一定是 100% 正确的,因为它将由人工手动验证,但我正在努力使该人的事情尽可能简单,并且有数千个条目要检查:)

【问题讨论】:

    标签: perl date nlp


    【解决方案1】:

    Date::Parse 肯定会成为您答案的一部分——它可以计算出一个随机格式化的类似日期的字符串,并从中得出一个实际可用的日期。

    您的问题的另一部分 - 文件名中的其余字符 - 非常不寻常,以至于您不太可能找到其他人为您打包了模块。

    在没有看到更多示例数据的情况下,实际上只能猜测,但我会首先确定可能或可能的“日期部分”候选者。

    这是一个使用 Date::Parse 的令人讨厌的蛮力示例(更聪明的方法是使用 regex-en 列表来尝试识别日期位 - 我很高兴消耗 CPU 周期而不是想那么难!)

    !/usr/bin/perl
    use strict;
    use warnings;
    use Date::Parse;
    
    my @files=("Report Aug06.xls", "ReportAug2006", "Report 11th September 2006.xls", 
               "Annual Report-08-06", "End-of-month Report01-08-06.xls", "Report2006");
    
    # assumption - longest likely date string is something like '11th September 2006' - 19 chars
    # shortest is "2006" - 4 chars.
    # brute force all strings from 19-4 chars long at the end of the filename (less extension)
    # return the longest thing that Date::Parse recognises as a date
    
    
    
    foreach my $file (@files){
      #chop extension if there is one
      $file=~s/\..*//;
      for my $len (-19..-4){
        my $string = substr($file, $len);
        my $time = str2time($string);
        print "$string is a date: $time = ",scalar(localtime($time)),"\n" if $time;
        last if $time;
        }
      }
    

    【讨论】:

    • 这有点类似于我最后的做法,但我的更长、更丑、更可怕​​:) 我暂时不回答这个问题,以防有人遇到之前的问题,但看起来有点像你自己的解决方案......
    • 你的回答基本正确;似乎没有任何库可以做到这一点,你必须自己做:)
    【解决方案2】:

    Date::Parse 做你想做的事。

    【讨论】:

    • Date::Parse 不能很好地处理字符串中的所有其他垃圾,所以我有 100% 的未定义率使用它;我需要一些足够聪明的东西来忽略杂物并找到约会。我想这与日期解析一样多的自然语言处理。
    【解决方案3】:

    DateTime::Format::Natural 看起来很适合这份工作。我不能亲自担保,但它有good reviews

    【讨论】:

    • 我确实遇到过,但是像 Date::Parse、Date::Manip 等它似乎要求字符串中的所有数据都与日期相关,而大部分内容我的字符串只是噪音(文件名的其他部分)。
    猜你喜欢
    • 1970-01-01
    • 2022-11-17
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2016-05-17
    相关资源
    最近更新 更多