1
votes

Comment obtenir la date du prochain janvier?

J'utilise DB2 et j'écris une requête SQL sur une table où j'ai une colonne pour chaque mois à venir. Comme, janvier, février, mars, avril, mai, etc. 12 au total.

Les données sont des prévisions de ventes pour les 12 prochains mois. Il est recalculé tous les soirs.

Par exemple, si le mois en cours est novembre 2019, la colonne novembre contient les prévisions pour novembre 2019, la colonne décembre pour décembre 2019, etc. Mais la colonne janvier contient des données pour janvier 2020.

Comment puis-je, en SQL, obtenir la date du mois à venir que la colonne représente?

J'ai besoin d'une fonction comme GetNextJanuary (), qui renvoie 20200101 si elle est utilisée cette année, et GetNextDecember () qui renvoie 20191201 etc. Cependant, si j'utiliserais GetNextJune () aujourd'hui, elle devrait renvoyer 20190601 (le mois en cours).

Est-ce possible en utilisant uniquement SQL?


0 commentaires

3 Réponses :


0
votes

Nous pouvons exprimer ce problème comme l'ajout d'une année à la date d'entrée, puis la tronquer au début de cette année:

SELECT
    DATE_TRUNC('YEAR', ADD_YEARS(CURRENT_DATE, 1))
FROM dual;


0 commentaires

0
votes

Vous pouvez utiliser la logique case :

select (case when month(current date) <= 1
             then to_date(year(current date) || '01-01', 'YYYY-MM-DD')
             else to_date(year(current date) + 1 || '01-01', 'YYYY-MM-DD')
        end) as jan_start_of_month,
       (case when month(current date) <= 2
             then to_date(year(current date) || '02-01', 'YYYY-MM-DD')
             else to_date(year(current date) + 1 || '02-01', 'YYYY-MM-DD')
        end) as feb_start_of_month,
       . . .


0 commentaires

0
votes
create or replace function GetNextMonth(p_month int)
returns date
deterministic
no external action
return 
  date(digits(dec(year(current date), 4))||'-'||digits(dec(p_month, 2))||'-01')
+ (case when p_month < month(current date) then 1 else 0 end) years;

select *
from table(values 
(getnextmonth(1), getnextmonth(12), getnextmonth(6))
) t (jan, dec, june);

JAN        DEC        JUNE
---------- ---------- ----------
2020-01-01 2019-12-01 2019-06-01
The logic is: if the month number passed (p_month) is less than current month, then we add 1 year to the date constructed from the 1-st day of the current year of the month number passed, and 0 years otherwise.

2 commentaires

Hmmm .... J'ajouterais probablement juste des années et des mois à une date "0" ( '2000-01-01' , très probablement), plutôt que de jouer avec les chiffres.


Votre solution pourrait-elle être plus rapide ou plus simple que celle-ci?