美文网首页小蒋同学
关于 PHP 时间戳最大支持到 2038 年问题解决办法

关于 PHP 时间戳最大支持到 2038 年问题解决办法

作者: 小蒋同学v | 来源:发表于2019-11-16 19:03 被阅读0次
    20191112215429.png

    原因分析

    这个问题在 64 位的 PHP 版本中并不存在,因为是在 32 位版本中,以秒计算 PHP 只支持到 2147483648,即:2^31,到 2038-01-19 03:14:08。

    Note:

    有效的时间戳通常从 Fri, 13 Dec 1901 20:45:54 GMT 到 Tue, 19 Jan 2038 03:14:07 GMT(对应于 32 位有符号整数的最小值和最大值)。不是所有的平台都支持负的时间戳,那么日记范围就被限制为不能早于 Unix 纪元。这意味着在 1970 年 1 月 1 日之前的日期将不能用在 Windows,一些 Linux 版本,以及几个其它的操作系统中。不过 PHP 5.1.0 及更新的版本克服了此限制。 —— [ PHP手册 ]

    解决办法

    如果在32系统PHP 5.1.0之后的版本,可以使用new DateTime解决。代码如下:

    将时间戳转为年月日:

    $d = new DateTime("@21474836490");
    $d->setTimezone(new DateTimeZone("PRC"));
    echo $d->format("Y-m-d H:i:s");
    

    将年月日转为时间戳:

    $d = new DateTime('2650-07-06 16:21:30');
    echo $d->format('U');
    

    如果运行时,遇到如下报错:

    WARNING: It is not safe to rely on the system’s timezone settings
    

    建议在 php.ini 里加上找到 date.timezone 项,设置 date.timezone = "Asia/Shanghai",再重启环境。

    利用 DateTime 的替代函数

    传统 date 替代函数:

    function newDate($curformat, $utc_value){
        while(1){
            if($utc_value > 2147483647){
                if(date('Y', $utc_value) < 2038){
                    $mydate2 = new DateTime('@'.$utcValue);
                    $string = $mydate2->format($curformat);
                    break;
                }
            }
            $string = date($curformat, $utc_value);
            break;
        }
        return $string;
    }
    
    // 调用方法
    $utc_value = 2247484647
    $curformat = 'Y-m-d';
    newDate($curformat, $utc_value);
    

    传统 strtotime 替代函数:

    function newStrToTime($str_time){
        $result = strtotime($str_time);
        if(empty($result)){
            $date = new DateTime($str_time);
            $result = $date->format('U');
        }
        return $result;
    }
    
    // 调用方法
    $str_time = '2100-10-02';
    newStrToTime($str_time);
    

    具体 DateTime 类使用方法请详查 - [ PHP手册-DateTime类 ]

    利用 DateTimeZone 的替代函数

    1、Unix时间戳转日期

    function unixtime_to_date($unixtime, $timezone = 'PRC') {
        $datetime = new DateTime("@$unixtime"); //DateTime类的bug,加入@可以将Unix时间戳作为参数传入
        $datetime->setTimezone(new DateTimeZone($timezone));
        return $datetime->format("Y-m-d H:i:s");
    }
    

    2、日期转Unix时间戳

    function date_to_unixtime($date, $timezone = 'PRC') {
        $datetime= new DateTime($date, new DateTimeZone($timezone));
        return $datetime->format('U');
    }
    

    相关文章

      网友评论

        本文标题:关于 PHP 时间戳最大支持到 2038 年问题解决办法

        本文链接:https://www.haomeiwen.com/subject/dgzyictx.html