表my_table是:
CREATE TABLE MY_TABLE(
ID NUMBER NOT NULL,
MY_DATE DATE NOT NULL);
输入以下查询:
select sysdate from dual
结果是:
10-MAG-12 21:22:32
请注意mag = may。
现在,如果我输入此查询:
select *
from my_table
where my_date <= sysdate
结果是:
9918 10-MAG-12 20:00:00
9915 10-MAG-12 21:00:00
9952 10-MAG-12 22:00:00
9951 10-MAG-12 23:00:00
请注意,在my_table中我只有这4条记录。为什么我只看到所有记录而不是第一和第二条记录?感谢。
我使用的是Oracle SQL Developer。
编辑:请注意,当我使用PL / SQL插入记录时,我输入类似的内容:
nCount NUMBER;
myDate DATE;
stringDate VARCHAR2(255);
BEGIN
nCount := 0;
stringDate := substr(to_char(trunc(sysdate)),0,9);
myDate := to_date(stringDate || ' 20:00:00','dd-mm-yyyy hh24:mi:ss');
for t in (a cursor) loop
insert into MY_TABLE(ID,MY_DATE)
values (9918,myDate+(nCount/1440));
nCount := nCount + 60;
end loop;
END;
答案 0 :(得分:3)
我怀疑存储在你的表中的数据没有2012年。它可能有一年的0012(两千年前)。
运行查询时看到的内容
SELECT id, to_char( my_date, 'dd-mm-yyyy hh24:mi:ss' )
FROM my_table
我希望年份将是0012而不是2012年。原因是您用于插入数据的代码错误地将日期转换为字符串而不使用显式格式掩码然后将字符串转换回来使用与会话NLS_DATE_FORMAT
不匹配的显式格式掩码的日期。一般来说,如果您发现自己将日期转换为字符串并返回日期,那么您可能做错了什么。如果您将代码更改为简单地进行日期操作,那么它将更有效,更强大,并且更不容易出错。
DECLARE
nCount NUMBER;
myDate DATE;
BEGIN
nCount := 0;
myDate := trunc(sysdate) + interval '20' hour;
for t in (a cursor) loop
insert into MY_TABLE(ID,MY_DATE)
values (9918,myDate+(nCount/1440));
nCount := nCount + 60;
end loop;
END;
了解原始代码出错的原因
stringDate := substr(to_char(trunc(sysdate)),0,9);
这需要SYSDATE
并将其截断到当天的午夜。到现在为止还挺好。然后,它调用TO_CHAR
而没有显式格式掩码。这会导致Oracle使用会话的NLS_DATE_FORMAT
,这意味着具有不同设置的不同用户将获得不同的结果。如果你的会话的NLS_DATE_FORMAT
恰好是'dd-mon-rr hh24:mi:ss',我猜是根据你发布的查询结果,这意味着该字符串的年份为2位数。您的SUBSTR
似乎假设输出只有两位数的年份(如果您有不同的NLS_DATE_FORMAT
,则您的SUBSTR
会产生不同的错误,例如可能会切断12 2012年只剩下20年的一年。
myDate := to_date(stringDate || ' 20:00:00','dd-mm-yyyy hh24:mi:ss');
假设stringDate
类似于10-MAG-12
,则下一行会生成字符串10-MAG-12 20:00:00
,然后尝试使用格式掩码dd-mm-yyyy hh24:mi:ss
将其转换为日期。这假定该字符串具有4位数年份,因此当它只找到2位数时,它假定您指的是12年,而不是2012年。