我今天遇到了一个奇怪的问题:我有一个被job调用的函数。我想找到从函数开始到结束的差别,然后记录到某个表。Oracle作业和查找时间戳差异
所以,让我们说我有功能
procedure p is
starttime timestamp := systimestamp;
procedure writeTime
is
diff interval day to second := systimestamp - starttime;
begin
-- here insert diff to some table
end;
begin
-- doing some long stuff
writeTime();
exception
when others then
writeTime();
end;
问题中的函数是:
当我手动运行此,它工作得很好,差别是显而易见的。例如。我用提取解析间隔:
extract(hour from diff)*60*60 + extract(minute from diff)*60 + extract(second from diff)
当我设置了作业和作业运行这个功能我有一个很大的问题:它返回负的结果,这是我,一些测试后,了解产生这里
systimestamp - starttime
。似乎这个计算中的systimestamp取自格林威治时区,而我的大小是一个小时,所以这个计算diff interval day to second := systimestamp - starttime;
返回的值是(-1小时+差)。
通过愚蠢的暴力破解我已经找到了解决办法:
procedure p is
starttime timestamp := systimestamp;
procedure writeTime
is
diff interval day to second;
endtime timestamp := systimestamp;
begin
diff := endtime - starttime;
-- here insert diff to some table
end;
begin
-- doing some long stuff
writeTime();
exception
when others then
writeTime();
end;
它只是在变量首先写入SYSTIMESTAMP,然后才计算差异。
我的数据库参数:
- 甲骨文11.2.0.2.0
- 时区+1柏林
所以,现在的问题是:我真的想知道是不是我的RDBMS的错误或者我可能没有看到一些明显的解释,为什么它是这样的?具体问题是:为什么这个操作
starttime timestamp := systimestamp;
它需要一个时区,并在此
diff interval day to second := systimestamp - starttime;
另需一个在使用相同的设置同一个会话的同一过程中?
和无论如何,我认为这是错误的,以允许从另一个数据类型减去,至少在这种情况下。它只能混淆... – smnbbrv
那么,这取决于编程语言的设计。在PL/SQL中允许隐式转换。例如,在C#中,它是不允许的,在VB.NET中,您可以在编译器设置中启用或禁用它。像往常一样,有没有它的优点和缺点。对于PL/SQL你只需要把它。 –