我希望能将PHP的microtime作为MySQL中的时间戳进行存储。
据说,最好使用DECIMAL
进行存储,但我找不到理想的大小。
有人知道microtime(true)
返回的最大值是多少吗?这样我就可以将其作为我的数据类型长度。
我应该选择可变的DECIMAL
长度吗?
简而言之,使用 microtime(false) 并将结果以一百万分之一秒为单位存储在 MySQL bigint 中。否则,您必须学习所有有关浮点运算的知识,这是一项非常复杂的任务。
PHP 的 microtime 函数从一个系统调用中获取 Unix 时间戳(目前约为十六进制 50eb7c00 或十进制 1,357,609,984),并从另一个系统调用中获取微秒时间。然后将它们转换成字符串。然后,如果使用 (true) 调用它,它会将该数字转换为一个 64 位 IEEE 745 浮点数,PHP 称之为 float
。
截止到今天,需要在小数点左侧使用十个十进制数字来存储整数 UNIX 时间戳。直到公元 2280 年左右,您的后代才需要十一位数字。需要使用小数点右侧六个数字来存储微秒。
您无法获得完全的微秒精度。大多数系统将其子秒系统时钟保留在范围为 1 到 33 毫秒之间的分辨率中。这取决于系统。
MySQL 版本 5.6.4 及更高版本允许您指定具有微秒分辨率的 DATETIME(6)
列。如果您正在使用此类 MySQL 版本,则绝对是最好的方式。
在版本 5.6.4 之前,您需要使用 MySQL DOUBLE
(IEEE 754 64 位浮点数)来存储这些数字。MySQL FLOAT
(IEEE 754 32 位浮点数)的幂指数不足以完全准确地存储当前秒的 UNIX 时间。
为什么要存储这些时间戳?您希望做什么?
WHERE table.timestamp = 1357609984.100000
或者类似的查询来查找特定的项目?如果在您的处理链中使用浮点数或双精度数(即使只使用 microtime(true)
一次),那么这是充满危险的。即使您认为它们应该相等,它们也会因为某些原因不相等而臭名昭著。相反,您需要使用像这样的东西。 0.001
被称为数字处理行业中的“epsilon”。
WHERE table.timestamp BETWEEN 1357609984.100000 - 0.001
AND 1357609984.100000 + 0.001
如果将时间戳存储为十进制或百万分之一秒的bigint
列,就不会出现这个问题。
IEEE 64位浮点数具有53位尾数 - 精度。当前的UNIX Epoch时间戳(自1970年1月1日00:00Z以来的秒数)乘以一百万使用了51位。因此,如果我们关心低位比特,DOUBLE中没有太多额外的精度。另一方面,对于几个世纪而言,精度不会耗尽。
int64(BIGINT)的精度远未用尽。如果我实际上只是为了在MySQL中对它们进行排序而存储微秒级时间戳,我会选择DATETIME(6)
,因为我可以免费获得许多日期算术运算。如果我正在做一个内存高负载应用程序,我会使用int64。
float
,MySQL double
)将正确排序。而浮点数的数值相等性则会变得比较棘手。 - O. JonesORDER BY
),那么使用DOUBLE
还是BIGINT
有关系吗? - user151841这取决于您需要的精度。如果毫秒足够,而且您不希望运行时间超过999999秒,您可以使用DECIMAL(10,4)
。您可以按照自己的需求进行调整。
关于理论最大值,它受系统上float
的大小限制(32位、64位)。有关详细信息,请参见PHP Float。但正如我所说,这是理论上的。没有计时器能以那种精度给出时间。
microtime(true)
的输出长度是否达到了最大值? - user1382306DATETIME
和TIMESTAMP
类型可以支持小数秒。因此,您可以在DATETIME(6)
或TIMESTAMP(6)
列中存储具有微秒分辨率的时间戳。
要将 PHP microtime()
返回值转换为 MySQL datetime 格式,您可以使用 MySQL FROM_UNIXTIME()
函数,或者如果您正在使用 PHP DateTime 类,则可以使用 DateTime::format()
。请注意,PHP date()
函数目前不支持微秒级时间戳。(它确实有一个微秒格式代码u
,但它总是将其映射到000000
。)
对于旧版 MySQL,无法在其本机 datetime 类型中存储微秒,您应该使用 DOUBLE
、BIGINT
(以微秒表示的值,即乘以 1,000,000)或 DECIMAL(16,6)
(这应该足够使用几百年)。
为什么不直接将其存储为 float
呢?这就是 microtime(true)
返回的内容,因此它是最佳选择。
FLOAT
是32位的,而PHP的float
则依赖于系统,但通常是64位的。 - O. Jones
14
,向左10个字符,向右4个字符。 - Samuel Cooktime()
,如果只有10位数字,而microtime()
则只会浮动4位小数。 - Samuel Cook