【问题标题】:How to iterate through range of Dates?如何遍历日期范围?
【发布时间】:2010-08-16 14:04:49
【问题描述】:

在我的脚本中,我需要遍历给定开始日期和结束日期的日期范围。如何在 Perl 中做到这一点?

【问题讨论】:

  • 日期的格式是什么? yyyy-mm-dd?
  • 格式应为 YYYY/MM/DD

标签: windows perl


【解决方案1】:

使用DateTime 模块。这是一个简单的例子,列出了前十天:

use 5.012;
use warnings;
use DateTime;

my $end = DateTime->now;
my $day = $end->clone->subtract( days => 10 );  # ten days ago

while ($day < $end) {
    say $day;
    $day->add( days => 1 );   # move along to next day
}

 

更新(在看到您的评论/更新后):

要解析日期字符串,然后查看模块 CPAN 上的 DateTime::Format

这是一个使用 DateTime::Format::DateParse 的示例,它解析 YYYY/MM/DD:

use DateTime::Format::DateParse;
my $d = DateTime::Format::DateParse->parse_datetime( '2010/06/23' );

【讨论】:

    【解决方案2】:

    一种简单的方法是使用Date::Simple 模块,它利用了运算符重载:

    use strict;
    use warnings;
    use Date::Simple;
    
    my $date    = Date::Simple->new ( '2010-01-01' );  # Stores Date::Simple object
    my $endDate = Date::Simple->today;                 # Today's date
    
    while ( ++$date < $endDate ) {
    
        print ( $date - $endDate ) , "day",
              ( ( $date-$endDate) == 1 ? '' : 's' ), " ago\n";
    }
    

    【讨论】:

      【解决方案3】:
      use DateTime::Format::Strptime qw();
      my $start = DateTime::Format::Strptime->new(pattern => '%Y/%m/%d')->parse_datetime('2010/08/16');
      my $end   = DateTime::Format::Strptime->new(pattern => '%Y/%m/%d')->parse_datetime('2010/11/24');
      
      while ($start < $end) {
          $start->add(days => 1);
          say $start->ymd('/');
      }
      

      【讨论】:

        【解决方案4】:

        我喜欢使用strftime 将为我标准化日期这一事实:

        #!/usr/bin/perl
        
        use strict;
        use warnings;
        
        use POSIX qw/strftime/;
        
        my $start = "2010/08/16";
        my $end   = "2010/09/16";
        
        my @time        = (0, 0, 0);
        my ($y, $m, $d) = split "/", $start;
        $y -= 1900;
        $m--;
        my $offset      = 0;
        
        while ((my $date = strftime "%Y/%m/%d", @time, $d + $offset, $m, $y) le $end) { 
            print "$date\n";
        } continue {
            $offset++;
        }
        

        【讨论】:

          【解决方案5】:

          你可以试试Date::Calc::Iterator

            # This puts all the dates from Dec 1, 2003 to Dec 10, 2003 in @dates1
            # @dates1 will contain ([2003,12,1],[2003,12,2] ... [2003,12,10]) ;
            my $i1 = Date::Calc::Iterator->new(from => [2003,12,1], to => [2003,12,10]) ;
            my @dates1 ;
            push @dates1,$_ while $_ = $i1->next ;
          

          【讨论】:

          • 当然,如果您只是要将值推送到数组,那么使用迭代器有什么意义呢?
          【解决方案6】:

          如果不建议安装额外的 perl 模块,可以使用这种方法,基于核心 perl 库POSIX

          #!/usr/bin/perl
          
          use strict;
          use warnings;
          use POSIX qw(strftime);
          
          # CREATE CALENDAR
          my @Calendar = ();
          my $years = 3;
          my @Now = localtime(); # An array of 9 date-time parameters.
          
          for my $count ( 0 .. ( 365 * $years ) ) {
              # If date is January 1st, manual shift to December 31st is needed,
              # because days ([yday][2]) are counted from January 31st and never shift back one year.
              if( $Now[4] == 0 && $Now[3] == 1 ) {
                  unshift @Calendar, strftime( "%Y-%m-%d", @Now );
                  $Now[5] --; # Reduce by one the sixth array element #5 - year.
                  $Now[4] = 11; # Set fifth array element № 4 - to December.
                  $Now[3] = 31; # Set fourth array element № 3 - to 31st.
              } else {
                  unshift @Calendar, strftime( "%Y-%m-%d", @Now );
                  $Now[3] --;
              }
          }
          
          # Print out.
          my $size = @Calendar;
          for (my $i = 0; $i < $size; $i++) {
              print $Calendar[$i]."\n";
          }
          

          【讨论】:

            【解决方案7】:

            Perl 具有丰富的时间和日期操作模块,如下所示:

            http://datetime.perl.org/?Modules

            还有一些日期和时间问题的例子。

            使用 Perl,总是有不止一种方法可以做到这一点。

            【讨论】:

              猜你喜欢
              • 1970-01-01
              • 2010-12-23
              • 1970-01-01
              • 2011-05-30
              • 2011-02-19
              • 1970-01-01
              • 2015-03-05
              • 2011-05-19
              相关资源
              最近更新 更多