DB2 将数字转换为日期

DB2 Convert Number to Date

出于某种原因(我对此无法控制),日期在我需要查询的 iSeries AS400 DB2 系统中存储为整数。例如。今天将存储为:

20,171,221

在英国,我需要日期格式如下所示:

21/12/2017

这是我的查询:(OAORDT = 日期字段)

Select
Date(SUBSTR( CHAR( OAORDT ),7,2) ||'/' || SUBSTR(CHAR ( OAORDT ),5,2) || '/' || SUBSTR(CHAR (OAORDT ),1,4)) AS "Order Date"
from some.table

但是,我得到的只是空值。如果我删除 Date 函数,那么它确实可以工作,但它现在是一个字符串,我不想要它:

Select
SUBSTR( CHAR( OAORDT ),7,2) ||'/' || SUBSTR(CHAR ( OAORDT ),5,2) || '/' || SUBSTR(CHAR (OAORDT ),1,4) AS "Order Date"
from some.table

如何将 OAORDT 字段转换为日期?

只是为了更新 - 我将使用 OpenQuery

从 MS SQL 服务器查询这个

谢谢。

请注意,您没有指定在哪里执行此操作,但由于您标记为 ibm-midrange,所以我回答嵌入式 SQL。如果你想要JDBC,或者ODBC,或者交互式SQL,概念是相似的,只是实现它的方式不同。

确保 SQL 使用正确格式的日期,默认为 *ISO。对你来说应该是 *EUR。在RPG中,你可以这样做:

exec sql set option *datfmt = *EUR;

确保 set option 是程序中的第一个 SQL 语句,我通常将它放在 D 和 C 规范之间。

注意这不是程序的最佳解决方案。最佳做法是将 RPG 和 SQL 日期格式都设置为 *ISO。我喜欢明确地这样做。 RPG 日期格式由

设置
ctl-opt DatFmt(*ISO);

SQL 日期格式由

设置
exec sql set option *datfmt = *ISO;

现在所有内部日期都以*ISO 格式处理,并且没有年份范围限制(年份可以是0001 - 9999)。您可以按照您喜欢的任何格式显示或打印。同样,您可以接收任何格式的输入。

编辑 日期是独一无二的野兽。不是每种语言,也不是 OS 知道如何处理它们。如果您要查找日期值,则需要指定的唯一格式是要转换为日期的字符串的格式。您不需要(不能)指定 Date 字段的内部格式,并且 Date 字段的外部格式几乎可以是您想要的任何格式,并且每次使用时都可以不同。所以当你像@Stavr00 提到的那样使用 TIMESTAMP_FORMAT() 时:

DATE(TIMESTAMP_FORMAT(CHAR(OAORDT),'YYYYMMDD'))

提供的格式不是日期字段的格式,而是要转换为 Timestamp 的数据的格式。然后 Date() 函数将 Timestamp 值转换为 Date 值。此时格式无关紧要,因为无论*DATFMT指定了哪种外部格式,时间戳都是内部时间戳格式,日期值是内部日期格式。下一次格式很重要是当您将 Date 值作为字符串或数字呈现给用户时。此时格式可以设置为*ISO*EUR*USA*JIS*YMD*MDY*DMY*JUL,在某些情况下 *LONGJUL*Cxxx 格式可用。

1) 如何将 OAORDT 字段转换为日期?
最简单的是使用 TIMESTAMP_FORMAT :

SELECT DATE(TIMESTAMP_FORMAT(CHAR(OAORDT),'YYYYMMDD'))

2) 在英国,我需要 [...] 日期格式 21/12/2017 :

SELECT VARCHAR_FORMAT(DATE(TIMESTAMP_FORMAT(CHAR(OAORDT),'YYYYMMDD')),'DD/MM/YYYY')

由于 none 种变体满足了我的需要,所以我推出了自己的变体。

就这么简单:

select * from yourschema.yourtable where yourdate = int(CURRENT DATE - 1 days) - 19000000;

days 是飞跃 year-aware 并且适合大多数需要。

同样的方法days可以变成monthsyears。 不需要VARCHAR_FORMAT/TIMESTAMP_FORMAT.

这样的重炮