【问题标题】:Converting string to Date and DateTime将字符串转换为日期和日期时间
【发布时间】:2011-09-08 12:01:07
【问题描述】:

如果我有一个 mm-dd-YYYY 格式的 PHP 字符串(例如,10-16-2003),我如何正确地将其转换为 Date,然后是 DateTime 格式为 @987654325 @?我要求DateDateTime 的唯一原因是我需要一个在一个位置,另一个在另一个位置。

【问题讨论】:

标签: php string datetime date


【解决方案1】:

在第一次约会时使用strtotime(),然后使用date('Y-m-d') 将其转换回来:

$time = strtotime('10/16/2003');

$newformat = date('Y-m-d',$time);

echo $newformat;
// 2003-10-16

请注意,在 strtotime() 函数中使用正斜杠 / 和连字符 - 是有区别的。引用php.net:

m/d/y 或 d-m-y 格式的日期 通过查看来消除歧义 各种分隔符 组件:如果分隔符是 斜线 (/),则美式 m/d/y 为 假定;而如果分隔符是 破折号 (-) 或点 (.),然后 假定为欧洲 d-m-y 格式。

为避免潜在的歧义,最好尽可能使用 ISO 8601 (YYYY-MM-DD) 日期或 DateTime::createFromFormat()。

【讨论】:

  • 这行不通。 PHP 会将该输入解释为 DD-MM-YYYY。
  • 我为我的代码添加了更多解释,感谢@konforce
  • 阅读下一个答案以获得更好的解决方案
  • @delive 您的日期字符串很可能不是正确的日期。
  • 它不起作用,因为这个答案具有误导性。 strtotime 接受某些格式。你怎么都喂不饱。这就是为什么应该使用DateTime::createFromFormat 而不是strtotime。可悲的是,这个答案有太多的赞成票,以至于任何人都无法关注。这些天都是复制粘贴。
【解决方案2】:

您需要小心使用 m/d/Y 和 m-d-Y 格式。 PHP 认为 / 表示 m/d/Y,- 表示 d-m-Y。在这种情况下,我会明确描述输入格式:

$ymd = DateTime::createFromFormat('m-d-Y', '10-16-2003')->format('Y-m-d');

这样你就不会随心所欲地做出某种解释。

【讨论】:

  • 很好奇为什么这不是公认的答案...这比依赖 strtotime() 函数的怪癖灵活得多。
  • 重要的是要指出 php DateTime 类从 PHP 5.2 开始可用,createFromFormat 从 5.3 开始提供
  • 与每个功能一样,您应该检查它是否满足您必须支持的最低版本。但是 PHP 5.2 EOL 是 2011 年 1 月。没有人应该再运行它了;迎合这些人只是让他们能够运行过时的、不安全的软件。
  • @Matthew 是的,正确。但是你现在从来没有,直到今天我发现仍然安装了一个PHP4.1版本...
  • 这应该是最佳答案+1
【解决方案3】:

要解析日期,您应该使用: 日期时间::createFromFormat();

例如:

$dateDE = "16/10/2013";
$dateUS = \DateTime::createFromFormat("d.m.Y", $dateDE)->format("m/d/Y");

但是,请小心,因为这会崩溃:

PHP Fatal error: Call to a member function format() on a non-object 

您实际上需要首先检查格式是否正常:

$dateDE = "16/10/2013";
$dateObj = \DateTime::createFromFormat("d.m.Y", $dateDE);
if (!$dateObj)
{
    throw new \UnexpectedValueException("Could not parse the date: $date");
}
$dateUS = $dateObj->format("m/d/Y");

现在您将得到一个异常,而不是崩溃,您可以捕获、传播等。

$dateDE 格式错误,应该是“16.10.2013”​​;

【讨论】:

  • 请注意,以这种方式检查 $dateObj 只会确保格式与掩码匹配,而不是日期实际有效。例如,像 99/99/2010 这样的日期将通过此检查,因为它与 m/d/Y 匹配,但它不是您通常希望允许的日期。这个答案解决了这种情况-> stackoverflow.com/a/10120725/995014
【解决方案4】:
$d = new DateTime('10-16-2003');

$timestamp = $d->getTimestamp(); // Unix timestamp
$formatted_date = $d->format('Y-m-d'); // 2003-10-16

编辑:您还可以将 DateTimeZone 传递给 DateTime() 构造函数,以确保创建所需时区的日期,而不是服务器默认时区。

【讨论】:

  • 我相信这会抛出异常,因为第 16 个月无效。
  • 重要的是要指出 php DateTime 类从 PHP 5.2 版开始可用,getTimestamp 从 5.3 版开始提供
【解决方案5】:

由于没有人提到这一点,这里是另一种方式:

$date = date_create_from_format("m-d-Y", "10-16-2003")->format("Y-m-d");

【讨论】:

    【解决方案6】:

    要从您可以使用的任何字符串创建日期:

    $date = DateTime::createFromFormat('d-m-y H:i', '01-01-01 01:00');
    echo $date->format('Y-m-d H:i');
    

    【讨论】:

      【解决方案7】:

      如果您的日期格式为“07/May/2018”并且需要将其转换为“2018-05-07”以便与 MySQL 兼容,您可以使用:

      if (!empty($date)) {
        $timestamp = strtotime($date);
        if ($timestamp === FALSE) {
          $timestamp = strtotime(str_replace('/', '-', $date));
        }
        $date = date('Y-m-d', $timestamp);
      }
      

      【讨论】:

        【解决方案8】:

        第一次约会

        $_firstDate = date("m-d-Y", strtotime($_yourDateString));
        

        新日期

        $_newDate = date("Y-m-d",strtotime($_yourDateString));
        

        【讨论】:

          【解决方案9】:

          如果您的格式为 dd-mm-yyyy,那么在 PHP 中它将无法按预期工作。在 PHP 文档中,他们有以下指南。

          m/d/y 或 d-m-y 格式的日期可以通过查看来消除歧义 各个组件之间的分隔符:如果分隔符是 斜线 (/),则假定为美式 m/d/y;而如果 分隔符是破折号 (-) 或点 (.),然后是欧洲 d-m-y 格式 假设。

          所以,你不能随意使用。当您尝试使用 dd/mm/yyyy 格式时,它将删除 FALSE。您可以通过以下方式进行调整。

          $date = "23/02/2013";
          $timestamp = strtotime($date);
          if ($timestamp === FALSE) {
            $timestamp = strtotime(str_replace('/', '-', $date));
          }
          echo $timestamp; // prints 1361577600
          

          【讨论】:

            【解决方案10】:

            如果您希望接受使用美式排序(月、日、年)的欧式格式(使用破折号或句点作为日、月、年)的日期同时仍接受其他格式 ,你可以扩展 DateTime 类:

            /**
             * Quietly convert European format to American format
             *
             * Accepts m-d-Y, m-d-y, m.d.Y, m.d.y, Y-m-d, Y.m.d
             * as well as all other built-in formats
             * 
             */
            class CustomDateTime extends DateTime 
            {
              public function __construct(string $time="now", DateTimeZone $timezone = null) 
              {
                // convert m-d-y or m.d.y to m/d/y to avoid PHP parsing as d-m-Y (substr avoids microtime error)
                $time = str_replace(['-','.'], '/', substr($time, 0, 10)) . substr($time, 10 );
            
                parent::__construct($time, $timezone);
              }
            }
            
            // usage:
            $date = new CustomDateTime('7-24-2019');
            print $date->format('Y-m-d');
            
            // => '2019-07-24'
            

            或者,您可以制作一个函数来接受 m-d-Y 并输出 Y-m-d:

            /**
             * Accept dates in various m, d, y formats and return as Y-m-d
             * 
             * Changes PHP's default behaviour for dates with dashes or dots.
             * Accepts:
             *   m-d-y, m-d-Y, Y-m-d,
             *   m.d.y, m.d.Y, Y.m.d,
             *   m/d/y, m/d/Y, Y/m/d,
             *   ... and all other formats natively supported 
             * 
             * Unsupported formats or invalid dates will generate an Exception
             * 
             * @see https://www.php.net/manual/en/datetime.formats.date.php PHP formats supported
             * @param  string $d various representations of date
             * @return string    Y-m-d or '----' for null or blank
             */
            function asYmd($d) {
              if(is_null($d) || $d=='') { return '----'; }
            
              // convert m-d-y or m.d.y to m/d/y to avoid PHP parsing as d-m-Y
              $d = str_replace(['-','.'], '/', $d);
            
              return (new DateTime($d))->format('Y-m-d');
            }
            
            // usage:
            
            <?= asYmd('7-24-2019') ?>
            
            // or
            
            <?php echo asYmd('7-24-2019'); ?>
            

            【讨论】:

              【解决方案11】:

              如果你想得到当月的最后一天,你可以用下面的代码来做。

              $last_day_this_month  = date('F jS Y', strtotime(date('F t Y')));
              

              【讨论】:

                【解决方案12】:

                我尝试了上述所有答案,但对我来说失败了,在我的情况下,我构建了一个函数,该函数获取具有以下格式的日期字符串 'YYYY/mm/dd' 。所以我认为像这样爆炸字符串会更好:

                $old_date = explode('/', $coming_date_str);
                

                $new_data = $old_date[0].'-'.$old_date[1].'-'.$old_date[2]; // 将字符串转换为上述所有帖子并完成

                $new_date = date('Y-m-d', strtotime($new_data));
                $new_date = DateTime::createFromFormat("Y-m-d", new_date);
                

                【讨论】:

                  猜你喜欢
                  • 1970-01-01
                  • 1970-01-01
                  • 2014-04-23
                  • 2015-09-17
                  • 1970-01-01
                  • 2021-05-31
                  • 2019-04-12
                  • 2015-03-24
                  • 2011-05-17
                  相关资源
                  最近更新 更多