dbf 文件(dBase 7 格式)中的时间戳字段没有意义



我看过 [1] 和 [2],我完全困惑(因为 dbf 文件是一个版本 4 文件,[1] 应该适用良好(。 一方面,为什么 [1] 声明时间戳的日期部分是自公元前 1 年 1 月 4713 日以来的 # 天? 这实在是太令人费解了。 其次,假设它是自公元前 4713 年以来的 # 天,我对我获得的值有一些麻烦。

首先,我的dbf文件有一个时间戳字段,该字段具有8字节长的值。 实际的 日期是 2000/8/16 17:21:41。 在 dbf 文件中,8 字节序列如下所示 0x42ccb20e0340df00。

从 [1] 开始,它表示前 4 个字节用于日期,第二个 4 个字节用于时间。 如果原件 字节序列实际上是小端序(0x42ccb20e(,那么这应该是0x0eb2cc42 来到246598722的价值。 所以日期是0x0eb2cc42(246598722(,时间是0x00df4003 (14630915(。

我一定在这里错过了什么或计算错了什么。 246598722相当于675612年(假设1年= 365天,因为添加闰年会让我感到困惑。而且真的不应该那么差(。

从 [2] 开始,我不应该使用 01/01/4173bc 作为基础,而是使用 12/31/1899(好吧,1/1/1900(。 但是,我拥有的日期值甚至不在 [2] 显示的范围内。

现在,如果我取实际值 (2000/8/16( 并使用 [1] 和 [2],我会得到以下内容:

方法[1]:2450501天:(2000 - -4713(*365+(8*30(+16 方法 [2]: 36756 天 : [100 * 365 + 8 * 30 + 16](多计 # 天(

dbf 文件没有损坏(否则,如果我查看 dBase 中的时间戳,它会废话 并显示一些疯狂的东西(。

我想过使用大端序,但这更没有意义,因为值更大。 我什至想到了它实际上是自任一日期以来经过的 # 秒的可能性,但这使得这些值的意义更小。 即 246598722 = # 经过的秒数(从 2000/8/16 开始倒计时(将使基准年为 1812 年。 (计算:246898722/(3600 * 365( = 187.8985,因此 2000 - 187.8985 = 1812.1015(

有人可以指出我做错了哪里吗?

谢谢!

[1] - https://www.dbase.com/Knowledgebase/INT/db7_file_fmt.htm [2] - 转换 dBase 时间戳

对于任何dBASE问题,我建议去dBASE新闻组,他们有一个非常有用和知识渊博的社区。

多亏了 [3],我终于找到了答案。

基本上,时间戳 8 字节序列作为一个整体使用,并带有以下注释:

  1. 它存储在大端序中。

  2. 不使用最后一个字节。

  3. 这是一个儒略日的数字。

所以就我而言,它是0x42ccb20e0340df00并截断最后一个字节, 我得到0x42ccb20e0340df。

然后以下 python 代码获取正确的信息:

import datetime
base = 0x42cc418ba99a00
frm_date = int('42ccb20e0340df', 16)
final_ts = (frm_date - base) / 500
final_date = datetime.datetime.utcfromtimestamp(final_ts)

输出 2000-8-16 17:21:41 和一些毫秒,我只是忽略了。

所以我猜理论是上面的代码将"基本"日期移动到 1970/1/1 从 1/1/1,这很有帮助,因为 utcfromtimestamp(( 没有 使用 1970/1/1 之前的任何值。

我的困惑源于它不使用 4713BC 作为 基准年,而是使用 1/1/1,尽管我仍在尝试弄清楚如何获取 1970/1/1 的值0x42cc418ba99a00。

[3] - https://stackoverflow.com/a/60424157/10860403

最新更新