Obtenir des Dates entre plusieurs dates

j'ai besoin d'obtenir toutes les dates présentes dans la plage de dates à l'aide de SQL Server 2005

15
demandé sur Thomas Bratt 2008-11-07 12:16:20

7 réponses

Ici, vous allez:

DECLARE @DateFrom smalldatetime, @DateTo smalldatetime;
SET @DateFrom='20000101';
SET @DateTo='20081231';
-------------------------------
WITH T(date)
AS
( 
SELECT @DateFrom 
UNION ALL
SELECT DateAdd(day,1,T.date) FROM T WHERE T.date < @DateTo
)
SELECT date FROM T OPTION (MAXRECURSION 32767);
57
répondu Incidently 2008-11-07 12:09:06

si vous avez les dates dans une table et que vous voulez simplement sélectionner celles entre deux dates, vous pouvez utiliser

select * from yourTable where yourDate between date1 and date2

si vous voulez produire les dates à partir de rien, vous pouvez le faire avec une boucle ou vous pouvez remplir une table temporaire avec des dates et ensuite sélectionner à partir de cela.

8
répondu Ed Guiness 2008-11-07 09:23:56
DECLARE @Date1 DATE='2016-12-21', @Date2 DATE='2016-12-25'
SELECT DATEADD(DAY,number,@Date1) [Date] FROM master..spt_values WHERE type = 'P' AND DATEADD(DAY,number,@Date1) <= @Date2
4
répondu Surinder Singh 2016-12-04 12:48:52

un peu plus compliqué mais peut-être plus flexible serait d'utiliser une table contenant un ensemble séquentiel de nombres. Cela permet de plus d'une plage de dates avec des intervalles différents.

/* holds a sequential set of number ie 0 to max */
/* where max is the total number of rows expected */
declare @Numbers table ( Number int  )

declare @max int 
declare @cnt int

set @cnt = 0
/* this value could be limited if you knew the total rows expected */
set @max = 999 

/* we are building the NUMBERS table on the fly */
/* but this could be a proper table in the database */
/* created at the point of first deployment */
while (@cnt <= @max)
begin
      insert into @Numbers select @cnt
      set @cnt = @cnt + 1
end

/* EXAMPLE of creating dates with different intervals */

declare @DateRanges table ( 
   StartDateTime datetime, EndDateTime datetime, Interval int )

/* example set of date ranges */
insert into @DateRanges
select '01 Jan 2009', '10 Jan 2009', 1 /* 1 day interval */
union select '01 Feb 2009', '10 Feb 2009', 2 /* 2 day interval */

/* heres the important bit generate the dates */
select
      StartDateTime
from
(
      select
            d.StartDateTime as RangeStart,
            d.EndDateTime as RangeEnd,
            dateadd(DAY, d.Interval * n.Number, d.StartDateTime) as StartDateTime
      from 
            @DateRanges d, @Numbers n
) as dates
where
      StartDateTime between RangeStart and RangeEnd
order by StartDateTime

j'utilise actuellementune variante de ceci pour diviser les dates en tranches de temps (avec divers intervalles, mais habituellement 5 minutes). Ma table @numbers contient un max de 288 car c'est le nombre total de 5 minutes de machines à sous que vous pouvez avoir dans une période de 24 heures.

/* EXAMPLE of creating times with different intervals */

delete from @DateRanges 

/* example set of date ranges */
insert into @DateRanges
select '01 Jan 2009 09:00:00', '01 Jan 2009 12:00:00', 30 /* 30 minutes interval */
union select '02 Feb 2009 09:00:00', '02 Feb 2009 10:00:00', 5 /* 5 minutes interval */

/* heres the import bit generate the times */
select
      StartDateTime,
      EndDateTime
from
(
      select
            d.StartDateTime as RangeStart,
            d.EndDateTime as RangeEnd,
            dateadd(MINUTE, d.Interval * n.Number, d.StartDateTime) as StartDateTime,
            dateadd(MINUTE, d.Interval * (n.Number + 1) , StartDateTime) as EndDateTime
      from 
            @DateRanges d, @Numbers n
) as dates
where
      StartDateTime >= RangeStart and EndDateTime <= RangeEnd
order by StartDateTime
1
répondu Chris Moutray 2015-06-13 14:02:57

Voici la version Oracle de date generation:

SELECT TO_DATE ('01-OCT-2008') + ROWNUM - 1 g_date
  FROM all_objects
 WHERE ROWNUM <= 15

au lieu de all_objects il peut être n'importe quelle table avec assez de lignes pour couvrir la gamme.

0
répondu user34850 2008-11-07 16:09:43

si ce que vous voulez est d'obtenir toutes les dates présentes dans votre base de données entre deux dates (c.-à-d. quelles dates les clients ont passé des commandes au troisième trimestre de 2008) vous écririez quelque chose comme ceci:

select distinct(orderPlacedDate) 
from orders 
where orderPlacedDate between '2008-07-01' and 2008-09-30' 
order by orderPlacedDate
-2
répondu Soraz 2017-08-31 16:34:10

Pour générer une plage de dates que vous pourriez écrire une fonction table. C'est une fonction qui crée une dimension de date pour un entrepôt de données - vous pouvez probablement s'adapter assez facilement par découper les promotions.

Edit: ici, il n'y a pas de hiérarchie des dimensions de date.

if object_id ('ods.uf_DateHierarchy') is not null
    drop function ods.uf_DateHierarchy
go

create function ods.uf_DateHierarchy (
       @DateFrom datetime
      ,@DateTo   datetime
) returns @DateHierarchy table (
        DateKey           datetime
) as begin
    declare @today           datetime  
    set @today = @Datefrom

    while @today <= @DateTo begin
        insert @DateHierarchy (DateKey) values (@today)
        set @today = dateadd (dd, 1, @today)
    end

    return
end

go
-3
répondu ConcernedOfTunbridgeWells 2008-11-07 15:29:37