【问题标题】:How Do I use the formats in DateTime::Locale with a DateTime object?如何将 DateTime::Locale 中的格式与 DateTime 对象一起使用?
【发布时间】:2013-11-04 11:15:18
【问题描述】:

DateTime::Locale 有一个非常全面的日期和时间格式列表,适用于各种地区和国家。我想在给客户的电子邮件中使用它,具体取决于客户来自哪个国家/地区。

不幸的是,从文档中很难理解如何将这些函数实际用于中长日期。例如,DateTime::Locale::de_DE 在文档中列出了这些date formats(摘录):

Long
 2008-02-05T18:30:30 = 5. Februar 2008
 1995-12-22T09:05:02 = 22. Dezember 1995
-0010-09-15T04:44:23 = 15. September -10

Medium
 2008-02-05T18:30:30 = 05.02.2008
 1995-12-22T09:05:02 = 22.12.1995
 -0010-09-15T04:44:23 = 15.09.-010

这太棒了。根据DateTime::Locale::Base,locale 对象中有一些方法可以获取这些格式:$locale->date_format_long()$locale->date_format_medium()

经过一番谷歌搜索后,我想到了Sinan Ünür's blog,他在其中显示了这段代码(摘录):

for my $locale ( qw(ar da de en_GB es fr ru tr) ) {
    $dt->set_locale( $locale );
    print_date( $dt );
}

sub print_date {
    my ($dt) = @_;
    my $locale = $dt->locale;

    printf(
        "In %s: %s\n", $locale->name,
        $dt->format_cldr($locale->date_format_full)
    );
}

所以这些方法产生的格式是cldr格式。凉爽的。但思南展示的东西看起来很乏味。简而言之,就是:

for (qw( ar da de en_GB es fr ru tr )) {
  my $dt2 = DateTime->now( locale => $_ );
  printf "%s: %s\n", $_, $dt2->format_cldr($dt2->locale->date_format_long);
}

为了更短,我当然可以这样做:

package DateTime;

sub stringify_long {
  return $_[0]->format_cldr($_[0]->locale->date_format_long);
}

package Main;
use strict; use warnings;    
use DateTime;

my $dt = DateTime->now( locale => 'de_DE' );
print $dt->stringify_long;

但我不想那样做。所以我的问题是:有没有办法使用我缺少的内置方法根据其中一种格式从其语言环境中对 DateTime 对象进行字符串化?

【问题讨论】:

    标签: perl datetime locale


    【解决方案1】:

    我不确定您对 Sinan Ünür 方法的反对意见是什么,所以我不知道这是否会吸引您,但您可以指定一个格式化程序对象来控制 DateTime 对象的字符串化:

    use DateTime;
    use DateTime::Format::CLDR;
    use DateTime::Locale;
    
    my $locale = DateTime::Locale->load('de_DE');
    my $formatter = DateTime::Format::CLDR->new(
        pattern => $locale->date_format_long,
        locale => $locale
    );
    my $dt = DateTime->now( locale => $locale, formatter => $formatter );
    print $dt;
    

    use DateTime;
    use DateTime::Format::CLDR;
    use DateTime::Locale;
    
    my $locale = DateTime::Locale->load('de_DE');
    my $dt = DateTime->now( locale => $locale );
    my $formatter = DateTime::Format::CLDR->new(
        pattern => $locale->date_format_long,
        locale => $locale
    );
    $dt->set_formatter($formatter);
    print $dt;
    

    这种方法的好处是,一旦您设置了格式化程序,打印日期就很容易了。

    【讨论】:

    • 格式化程序似乎是一个不错的选择。感谢您展示它。如果我经常做这种事情,我主要是在寻找一个更少重复的选项。
    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2019-10-11
    • 2015-10-06
    • 2015-12-02
    • 1970-01-01
    相关资源
    最近更新 更多