Dies liegt daran, dass Sie implizite Datumsumwandlungen durchführen, und Ihr NLS_DATE_FORMAT
hat ein zweistelliges Jahr, z. 'DD/MM/YY'
oder diese:
alter session set nls_date_format = 'DD-Mon-RR';
-- CTE to generate two dummy values
with RM (REME_FECHA_ENTREGA) as (
select date '1950-01-01' from dual
union all select date '1950-01-02' from dual
)
-- your query plus the original date value
select to_char(RM.REME_FECHA_ENTREGA, 'SYYYY-MM-DD') as REME_FECHA_ENTREG,
to_char((
CASE
WHEN to_date(RM.REME_FECHA_ENTREGA,'DD/MM/YYYY') <= to_date('01/01/1950','DD/MM/YYYY')
THEN
to_date('01/01/2999','DD/MM/YYYY')
ELSE
to_date(RM.REME_FECHA_ENTREGA,'DD/MM/YYYY')
END) ,'DD/MM/YYYY')
as FechaEntregaRemesa
from rm;
REME_FECHA_ FECHAENTRE
----------- ----------
1950-01-01 01/01/2999
1950-01-02 01/01/2999
Mit einem 4-stelligen Format funktioniert es wie erwartet:
alter session set nls_date_format = 'DD/MM/YYYY';
...
REME_FECHA_ FECHAENTRE
----------- ----------
1950-01-01 01/01/2099
1950-01-02 02/01/1950
Wenn Sie das tun
to_date(RM.REME_FECHA_ENTREGA,'DD/MM/YYYY')
Sie eigentlich wirklich tun:
to_date(to_char(RM.REME_FECHA_ENTREGA, '<NLS_DATE_FORMAT>'),'DD/MM/YYYY')
weshalb yo Sie sehen das Problem mit einem zweistelligen Jahresmodell. Die implizite to_char(RM.REME_FECHA_ENTREGA, 'DD-MON-RR')
gibt eine Zeichenfolge wie '01-JAN-50'
. Wenn Sie diese Zeichenfolge wieder in to_date()
mit einem YYYY
Format Modell übergeben Sie es als Jahr 0050 interpretiert hat, so es wird immer vor 1950
"Oracle Database converts strings to dates with some flexibility", die nicht immer hilfreich ist ... hier ist es nicht beschweren, dass Sie habe für ein 4-stelliges Modell zwei Ziffern angegeben oder in meinem Beispiel eine Monatsabkürzung anstelle einer Monatszahl. (Sie können das Verhalten mit den FM/FX-Modifikatoren ändern, aber es ist standardmäßig flexibel.)
Sie könnten versucht sein, alter session
zu verwenden, wie ich für diese Demo getan habe, aber sollte nicht auf NLS-Einstellungen verlassen, wie Sie normalerweise haben keine Kontrolle über die Einstellungen anderer Benutzer. (Ich vermute, Sie wussten nicht, dass Sie in dieser Abfrage waren, aber es ist immer noch etwas, worauf Sie achten sollten.) Verwenden Sie immer explizite Konvertierungen und Vollformat-Modelle, wenn Sie Datumsangaben in Zeichenfolgen und umgekehrt konvertieren müssen.
Sie müssen jedoch Ihren vorhandenen Datumswert überhaupt nicht konvertieren. Es ist ein Date, also lass es in Ruhe.Sie können auch Datumsliterale für die festen Werte verwenden, um Unklarheiten zu vermeiden und für ein bisschen weniger tippen:
to_char(
CASE
WHEN RM.REME_FECHA_ENTREGA <= date '1950-01-01'
THEN
date '2099-01-01'
ELSE
RM.REME_FECHA_ENTREGA
END,'DD/MM/YYYY')
as FechaEntregaRemesa
...
REME_FECHA_ FECHAENTRE
----------- ----------
1950-01-01 01/01/2099
1950-01-02 02/01/1950
oder sogar (@ expenguin Vorschlag zu ändern) nur Daten verwenden, wenn Sie müssen:
CASE
WHEN RM.REME_FECHA_ENTREGA <= date '1950-01-01'
THEN
'01/01/2099'
ELSE
TO_CHAR(RM.REME_FECHA_ENTREGA, 'DD/MM/YYYY')
END as FechaEntregaRemesa
Bitte bearbeiten Sie Ihre Frage, um die Definitionsdaten der Tabelle (oder zumindest der Spalte) und die Probendaten und die erwarteten Ergebnisse einzubeziehen. Und Ihre aktuelle NLS_DATE_FORMAT-Einstellung. Ich werde auf einen Ast gehen und vorschlagen, dass es DD-MON-RR ist, oder zumindest etwas mit einer 2-stelligen Jahr-Maske? Welchen Client verwenden Sie, um das auszuführen? –
Nach seinem Namen 'REME_FECHA_ENTREGA' ist ein ** DATUM **. Was soll 'TO_DATE' damit anfangen? Oder speichern Sie Ihre Daten als Zeichenfolgen? –
Wenn sie als Strings - in diesem Format sowieso - gespeichert wurden, würde die Abfrage das gewünschte Ergebnis erhalten, wie es ist. Das Konvertieren nach Datum in den Fallzweigen und dann zurück zu String wäre natürlich immernoch sinnlos. Ich denke, das ist nur ein (ziemlich häufiges) Missverständnis darüber, wie Datumsformatierung funktioniert. –