Anda dapat mengonversi stempel waktu Anda dengan zona waktu ke UTC, lalu kurangi epoch dari itu:
select timestamp '2018-10-19 09:12:47.0 AMERICA/DENVER'
- timestamp '1970-01-01 00:00:00.0 UTC' as diff
from dual;
yang memberi Anda tipe data interval:
DIFF
----------------------
+17823 15:12:47.000000
Anda kemudian dapat mengekstrak elemen dari itu, dan mengalikan setiap elemen dengan faktor yang sesuai untuk mengubahnya menjadi milidetik (yaitu selama berhari-hari, 60*60*24*1000); lalu tambahkan bersama-sama:
select extract(day from diff) * 86400000
+ extract(hour from diff) * 3600000
+ extract(minute from diff) * 60000
+ extract(second from diff) * 1000 as unixtime
from (
select timestamp '2018-10-19 09:12:47.0 AMERICA/DENVER'
- timestamp '1970-01-01 00:00:00.0 UTC' as diff
from dual
);
UNIXTIME
--------------------
1539961967000
Ini juga mempertahankan milidetik, jika stempel waktu awal memilikinya (ini mengonversi dari waktu 'Unix' sambil mempertahankannya):
select (timestamp '1970-01-01 00:00:00.0 UTC' + (1539961967567 * interval '0.001' second))
at time zone 'America/Denver' as denver_time
from dual;
DENVER_TIME
--------------------------------------------
2018-10-19 09:12:47.567000000 AMERICA/DENVER
kemudian untuk mengonversi kembali:
select extract(day from diff) * 86400000
+ extract(hour from diff) * 3600000
+ extract(minute from diff) * 60000
+ extract(second from diff) * 1000 as unixtime
from (
select timestamp '2018-10-19 09:12:47.567 AMERICA/DENVER'
- timestamp '1970-01-01 00:00:00.0 UTC' as diff
from dual
);
UNIXTIME
--------------------
1539961967567
Jika stempel waktu awal Anda memiliki presisi yang lebih besar dari itu, maka Anda harus memotong (atau bulat/lantai/ceil/cast) untuk menghindari hasil non-integer; versi ini hanya memotong bagian milidetik yang diekstraksi:
select diff,
extract(day from diff) * 86400000
+ extract(hour from diff) * 3600000
+ extract(minute from diff) * 60000
+ trunc(extract(second from diff) * 1000) as unixtime
from (
select timestamp '2018-10-19 09:12:47.123456789 AMERICA/DENVER'
- timestamp '1970-01-01 00:00:00.0 UTC' as diff
from dual
);
DIFF UNIXTIME
------------------------- --------------------
+17823 15:12:47.123456789 1539961967123
Tanpa pemotongan itu (atau yang setara), Anda akan mendapatkan 1539961967123.456789
.
Aku lupa tentang perbedaan detik kabisat; jika Anda perlu/ingin menanganinya, lihat jawaban ini .