SQL Loader Timestamp转UNIX时间

SQL Loader Timestamp to UNIX time

我有一个用于 sql 加载程序的工作控制文件,我可以在其中以我希望的各种格式上传我的时间戳。

 my_timestamp  TIMESTAMP \"dd-MON-yy hh.mi.ss.ff6 PM\",

但我想以毫秒为单位将我的 .csv 文件中的时间戳上传到我的数据库中的 NUMBER 字段中。如果可能的话有什么建议吗?

我假设您想去掉毫秒部分并单独存储。

未测试:

...
my_timestamp    TIMESTAMP  "dd-MON-yy hh.mi.ss.ff6 PM"
my_milliseconds NUMBER     "regexp_substr(:my_timestamp, '\.(\d+) ', 1,1,null,1)"
...

但这行得通,所以上面的应该行得通:

select regexp_substr('07-JAN-14 04.24.00.123456 PM', '\.(\d+) ', 1,1,null,1) 
from dual; 

Returns 第一个组(用括号括起来)匹配一个或多个数字的字符串模式,左边是句点,右边是 space。

编辑:哦,您需要将整个时间戳转换为 UNIX 时间,这是自 1/1/1970 0:0:0(纪元)以来的秒数。

首先您需要将日期转换为 UNIX 时间的公式。稍微谷歌一下就发现了这个:

SELECT (cast(to_timestamp('14.03.2010 08:16:22.123456 AM','dd.mm.yyyy hh:mi:ss.FF6 AM')as date) - TO_DATE('01/01/1970 00:00:00', 'MM-DD-YYYY HH24:MI:SS')) *
24 * 60 * 60 
FROM DUAL;

结果为“1268554582”。使用纪元转换器将此 UNIX 时间转换回日期:http://www.epochconverter.com/ 验证返回了正确的日期。

那么,在控制文件中如何使用呢?如果可以像上面那样select,可以这样放到控制文件中:

...
my_timestamp    TIMESTAMP  "dd-MON-yy hh.mi.ss.ff6 PM"
my_unixtime     NUMBER     "(cast(:my_timestamp)as date) - TO_DATE('01/01/1970 00:00:00', 'MM-DD-YYYY HH24:MI:SS')) *
24 * 60 * 60"
...

您可能需要 EXPRESSION 关键字,我不确定:

my_unixtime NUMBER  EXPRESSION "(cast(:my_timestamp)as date) - TO_DATE('01/01/1970 00:00:00', 'MM-DD-YYYY HH24:MI:SS')) *
24 * 60 * 60"

现在这适用于一列,但如果有很多,或者您想重用它怎么办?为了重用和可维护性,使用接受时间戳和 returns unixtime 的函数将代码放在一个地方,如上所述,然后从您的控制文件中调用它:

...
my_timestamp    TIMESTAMP  "dd-MON-yy hh.mi.ss.ff6 PM"
my_unixtime     NUMBER     "my_timestamp_to_unix_converter(:my_timestamp)"
...

注意事项:

毫秒丢失,因为 UNIX 时间是自 1/1/1970 以来的秒数,而不是毫秒数。如果毫秒对你很重要,你可能需要单独保存它们,如上所示。

2038 年到来时可能会有麻烦:http://en.wikipedia.org/wiki/Year_2038_problem

资源:

http://www.epochconverter.com/

http://orcasoracle.squarespace.com/oracle-rdbms/2009/10/9/converting-timestamp-to-date.html

https://community.oracle.com/thread/1045221