将sysdate转换为bst(英国夏令时)

cetgtptt  于 2021-08-13  发布在  Java
关注(0)|答案(2)|浏览(288)

我有一个javaapi,它从位于et时区的oracle数据库获取数据。我想在2列上使用sysdate查询该表,但是sysdate应该被选为当前bst date值,而不是et date值。

select * from customers where sysdate between mem_registered_date and mem_deregistered_date;

如何做到这一点?请帮忙

wbrvyc0a

wbrvyc0a1#

在时区之间进行转换的最简单方法是使用一种理解时区的数据类型,即 TIMESTAMP . 当你转换到你想要的时区时 CAST 它回到了一个 DATE 数据类型:

SELECT *
FROM   customers
WHERE  CAST( SYSTIMESTAMP AT TIME ZONE 'Europe/London' AS DATE )
         BETWEEN mem_registered_date AND mem_deregistered_date;

我假设您想要英国的当前时间(夏季为bst,冬季为gmt),如果您想要时区utc+1,则使用:

CAST( SYSTIMESTAMP AT TIME ZONE '+01:00' AS DATE )
bttbmeg0

bttbmeg02#

如果查询的列具有仅日期的值,不包含任何时间或时区,即与sql标准类似类型的列 DATE 键入,然后使用java类 LocalDate .
一般来说,最好使用时间跨度的半开定义,其中开始是包含的,而结束是独占的。这使得跨度几乎彼此相邻,没有间隙或重叠。所以永远不要使用sql命令 BETWEEN 对于日期时间范围,因为它是完全关闭的(包括开始和结束)。
获取今天的日期,如特定地区(时区)的人们使用的挂钟时间所示。 BST 不是真正的时区。对于英国时间,使用 Europe/London .

ZoneId z = ZoneId.of( "Europe/London" ) ;
LocalDate today = LocalDate.now( z ) ;

sql将如下所示:

SELECT * 
FROM event_ 
WHERE ? >= start_
AND ? < end_
;

填写占位符。

myPreparedStatement.setObject( 1 , today ) ;
myPreparedStatement.setObject( 2 , today ) ;

将数据库中的日期值加载到java中。

LocalDate start = myResultSet.getObject( … , LocalDate.class ) ;

不带时区的时间戳

这个名字不正确 DATE 在oracle数据库中,实际上表示一个带有日期时间的日期,没有时区上下文或utc偏移量。因此,这种类型不能代表一个时刻,时间线上的一个特定点。它的价值是明年1月23日中午,我们无法知道这是在东京,图卢兹,还是托莱多中午-所有不同的时刻相隔数小时。这个 DATE 类型类似于sql标准类型 TIMESTAMP WITHOUT TIME ZONE .
所以对于这种数据类型,你问的关于时区的问题毫无意义。苹果和橙子。涉及时区意味着你在追踪时刻,时间线上的特定点。但是Oracle DATE 不能像上面讨论的那样表示时刻。
要跟踪时刻,应该使用类似于sql标准的列类型 TIMESTAMP WITH TIME ZONE .

相关问题