2013-07-08 43 views
14

Tôi muốn liệt kê ngày tháng giữa hai ngày trong thủ tục được lưu trữ SQL Server.Cách liệt kê tất cả các ngày giữa hai ngày

Ví dụ:

Date1: 2015-05-28 
Date2: 2015-05-31 

Kết quả:

2015-05-29 
2015-05-30 

Làm thế nào để tính toán tất cả các ngày giữa hai ngày nhất định?

Kính trọng,

+0

http://www.sqlperformance.com/2013/01/t-sql-queries/ generate-a-set-3 –

Trả lời

14

Tạo một thủ tục lưu trữ mà không giống như sau:

declare @startDate date; 
declare @endDate date; 

select @startDate = '20150528'; 
select @endDate = '20150531'; 

with dateRange as 
(
    select dt = dateadd(dd, 1, @startDate) 
    where dateadd(dd, 1, @startDate) < @endDate 
    union all 
    select dateadd(dd, 1, dt) 
    from dateRange 
    where dateadd(dd, 1, dt) < @endDate 
) 
select * 
from dateRange 

SQL Fiddle with demo.

Hoặc tốt hơn là vẫn tạo bảng lịch và chỉ cần chọn từ đó.

+4

Tôi nghĩ rằng mọi cơ sở dữ liệu phải có bảng lịch –

+1

Hãy xem xét 'tùy chọn (tối đa 32767) ' – user443854

29

Bạn có thể sử dụng một bảng số:

DECLARE @Date1 DATE, @Date2 DATE 
SET @Date1 = '20150528' 
SET @Date2 = '20150531' 

SELECT DATEADD(DAY,number+1,@Date1) [Date] 
FROM master..spt_values 
WHERE type = 'P' 
AND DATEADD(DAY,number+1,@Date1) < @Date2 

Kết quả:

╔════════════╗ 
║ Date ║ 
╠════════════╣ 
║ 2015-05-29 ║ 
║ 2015-05-30 ║ 
╚════════════╝ 
+2

Tôi sẽ không làm điều đó. nếu tôi không có quyền truy cập vào 'chủ nhân' thì sao? –

+1

@LuisLL Đó chỉ là ví dụ nhanh về bảng số, op có thể sử dụng bất kỳ bảng nào khác hoặc bảng lịch. Nó thường nhanh hơn CTE đệ quy (mặc dù tôi thích sử dụng chúng, tôi biết chúng mang lại các vấn đề hiệu suất) – Lamak

+0

Có giới hạn nếu bạn cần có phạm vi ngày dài ... như 15-20 năm. Vì nó đang sử dụng bảng master..spt_values – gmsi

19

Sử dụng này,

DECLARE @start_date DATETIME = '2015-02-12 00:00:00.000'; 
DECLARE @end_date DATETIME = '2015-02-13 00:00:00.000'; 

WITH AllDays 
      AS (SELECT @start_date AS [Date], 1 AS [level] 
       UNION ALL 
       SELECT DATEADD(DAY, 1, [Date]), [level] + 1 
       FROM  AllDays 
       WHERE [Date] < @end_date) 
    SELECT [Date], [level] 
    FROM AllDays OPTION (MAXRECURSION 0) 

vượt qua @start_date@end_date như thông số SP.

Kết quả:

Date     level 
----------------------- ----------- 
2015-02-12 00:00:00.000 1 
2015-02-13 00:00:00.000 2 

(2 row(s) affected) 
0

Bạn có thể tạo một thủ tục lưu trữ qua 2 ngày

CREATE PROCEDURE SELECTALLDATES 
(
@StartDate as date, 
@EndDate as date 
) 
AS 
Declare @Current as date = DATEADD(DD, 1, @BeginDate); 

Create table #tmpDates 
(displayDate date) 

WHILE @Current < @EndDate 
BEGIN 
insert into #tmpDates 
VALUES(@Current); 
set @Current = DATEADD(DD, 1, @Current) -- add 1 to current day 
END 

Select * 
from #tmpDates 

drop table #tmpDates 
Các vấn đề liên quan