获取ID日期和正负天数之间的日期
Get dates between date of ID and date of plus or minus days
我有以下示例数据:
CREATE TABLE tblDates
(
ID int,
Dates DATE
);
SELECT * FROM tblDates
INSERT INTO tblDates VALUES(1,'2019-12-01');
INSERT INTO tblDates VALUES(2,'2019-12-05');
INSERT INTO tblDates VALUES(3,'2019-12-02');
INSERT INTO tblDates VALUES(4,'2019-12-09');
INSERT INTO tblDates VALUES(5,'2019-12-11');
我在这里寻找 ID = 4
的 date
和正负第 1,2,....n 天之间的日期。
尝试 1:我尝试使用 UNION ALL。
SELECT Dates FROM tblDates WHERE ID = 4
UNION ALL
SELECT DATEADD(day,1,Dates) FROM tblDates WHERE ID = 4;
当我寻找 50 天或更多天数差异时,此方法不适用。
尝试 2:
SELECT Dates FROM tblDates WHERE ID = 4 AND Dates between Dates AND DATEADD(day,1,Dates);
有单身约会。
尝试 3:
创建的函数:获取日期的函数
CREATE FUNCTION udf_GetDates(@MinDate DATE,@MaxDate DATE)
RETURNS TABLE
AS
RETURN
SELECT TOP (DATEDIFF(DAY, @MinDate, @MaxDate) + 1)
Date = DATEADD(DAY, ROW_NUMBER() OVER(ORDER BY a.object_id) - 1, @MinDate)
FROM sys.all_objects a
CROSS JOIN sys.all_objects b;
查询:
SELECT f.*
FROM udf_GetDates(t.Dates,DATEADD(day,1,t.Dates)) f
INNER JOIN tblDates t ON f.[Date] = t.[Dates]
WHERE t.ID = 4
出现错误:
Msg 4104, Level 16, State 1, Line 2 The multi-part identifier
"t.Dates" could not be bound. Msg 4104, Level 16, State 1, Line 2 The
multi-part identifier "t.Dates" could not be bound.
预期输出:
给定:ID = 4 和 day=+1
Dates
-----------
2019-12-09
2019-12-10
给定:ID = 4 和 day=+10
Dates
-----------
2019-12-09
2019-12-10
2019-12-11
2019-12-12
2019-12-13
2019-12-14
2019-12-15
2019-12-16
2019-12-17
2019-12-18
给定:ID = 4 和 day=-5
Dates
----------
2019-12-05
2019-12-06
2019-12-07
2019-12-08
2019-12-09
我尝试使用其他格式创建函数
create FUNCTION udf_GetDates(@MinDate DATE,@MaxDate DATE)
RETURNS @_result table (dt date)
AS
begin
insert into @_result
SELECT TOP (DATEDIFF(DAY, @MinDate, @MaxDate) + 1)
Date = DATEADD(DAY, ROW_NUMBER() OVER(ORDER BY a.object_id) - 1, @MinDate)
FROM sys.all_objects a
CROSS JOIN sys.all_objects b;
return
end
和select这样的结果
declare @_date date=(select Dates from tblDates where ID=4)
select *
from udf_GetDates(@_date,DATEADD(day,1,@_date))
我得到了你想要的结果
dt
2019-12-09
2019-12-10
试试这个查询
函数
CREATE FUNCTION udf_GetDates (@StartDate DATE, @Range INT)
RETURNS TABLE
AS
RETURN
SELECT
DATEADD(DAY, nbr - 1, @StartDate) myDate
FROM
(SELECT
ROW_NUMBER() OVER (ORDER BY c.object_id) AS Nbr
FROM
sys.columns c) nbrs
WHERE
nbr - 1 <= @Range
查询用法#1:
SELECT f.myDate
FROM udf_GetDates((SELECT dates FROM tblDates WHERE ID = 4), 2) f
查询用法#2:
SELECT t.*, P.*
FROM tblDates t
OUTER APPLY udf_GetDates(t.Dates, 5) p
WHERE t.ID = 4
更新的答案:
下一个日期
CREATE FUNCTION udf_GetDates (@StartDate DATE, @Range INT)
RETURNS TABLE
AS
RETURN
SELECT
DATEADD(DAY, nbr - 1, @StartDate) myDate
FROM
(SELECT
ROW_NUMBER() OVER (ORDER BY c.object_id) AS Nbr
FROM
sys.columns c) nbrs
WHERE
nbr - 1 <= @Range
以前的日期
CREATE FUNCTION [udf_GetDates_Minuus] (@StartDate DATE, @Range INT)
RETURNS TABLE
AS
RETURN
SELECT
DATEADD(DAY, -(nbr - 1), @StartDate) myDate
FROM
(SELECT
ROW_NUMBER() OVER (ORDER BY c.object_id) AS Nbr
FROM
sys.columns c) nbrs
WHERE
nbr - 1 <= @Range
单个函数中的下一个和上一个日期
CREATE FUNCTION udf_GetDatesNextandPrevious(@StartDate DATE, @Range INT)
RETURNS TABLE
AS
RETURN
SELECT
DATEADD(DAY, nbr - 1, @StartDate) myDate
FROM
(SELECT
ROW_NUMBER() OVER (ORDER BY c.object_id) AS Nbr
FROM
sys.columns c) nbrs
WHERE
nbr - 1 <= @Range
UNION
SELECT
DATEADD(DAY, -(nbr - 1), @StartDate) myDate
FROM
(SELECT
ROW_NUMBER() OVER (ORDER BY c.object_id) AS Nbr
FROM
sys.columns c) nbrs
WHERE
nbr - 1 <= @Range
这 SQL 将 return 两个范围之间的正确日期。只需根据您的需要进行调整即可。
DECLARE @From DATETIME,
@To DATETIME
SELECT @From = '2019-11-13',
@To = '2019-11-19'
;WITH Numbers AS
(
SELECT 0 AS Number
UNION ALL
SELECT Number + 1 AS Number
FROM Numbers
WHERE Number < DATEDIFF(d, @From, @To)
)
SELECT DATEADD(d,
Number, @From) AS Date
FROM Numbers
-- 结果
2019-11-13 00:00:00.000
2019-11-14 00:00:00.000
2019-11-15 00:00:00.000
2019-11-16 00:00:00.000
2019-11-17 00:00:00.000
2019-11-18 00:00:00.000
2019-11-19 00:00:00.000
在 sql 服务器中尝试此代码
DECLARE @selecteddate DATE
DECLARE @day INT = 10
DECLARE @id INT = 4;
DECLARE @count INT = 0;
DECLARE @table1 TABLE
(
date_ DATETIME
)
SELECT @selecteddate = dates
FROM tbldates
WHERE id = @id;
IF( @count <= @day )
BEGIN
if(@day > 1)
begin
set @day = @day - 1
end
WHILE @count <= @day
BEGIN
INSERT INTO @table1
VALUES (Dateadd(day, @count, @selecteddate))
SET @count = @count + 1
END
END
ELSE
BEGIN
WHILE @count > @day
BEGIN
INSERT INTO @table1
VALUES (Dateadd(day, @count, @selecteddate))
SET @count = @count - 1
END
END
SELECT *
FROM @table1
ORDER BY 1
我有以下示例数据:
CREATE TABLE tblDates
(
ID int,
Dates DATE
);
SELECT * FROM tblDates
INSERT INTO tblDates VALUES(1,'2019-12-01');
INSERT INTO tblDates VALUES(2,'2019-12-05');
INSERT INTO tblDates VALUES(3,'2019-12-02');
INSERT INTO tblDates VALUES(4,'2019-12-09');
INSERT INTO tblDates VALUES(5,'2019-12-11');
我在这里寻找 ID = 4
的 date
和正负第 1,2,....n 天之间的日期。
尝试 1:我尝试使用 UNION ALL。
SELECT Dates FROM tblDates WHERE ID = 4
UNION ALL
SELECT DATEADD(day,1,Dates) FROM tblDates WHERE ID = 4;
当我寻找 50 天或更多天数差异时,此方法不适用。
尝试 2:
SELECT Dates FROM tblDates WHERE ID = 4 AND Dates between Dates AND DATEADD(day,1,Dates);
有单身约会。
尝试 3:
创建的函数:获取日期的函数
CREATE FUNCTION udf_GetDates(@MinDate DATE,@MaxDate DATE)
RETURNS TABLE
AS
RETURN
SELECT TOP (DATEDIFF(DAY, @MinDate, @MaxDate) + 1)
Date = DATEADD(DAY, ROW_NUMBER() OVER(ORDER BY a.object_id) - 1, @MinDate)
FROM sys.all_objects a
CROSS JOIN sys.all_objects b;
查询:
SELECT f.*
FROM udf_GetDates(t.Dates,DATEADD(day,1,t.Dates)) f
INNER JOIN tblDates t ON f.[Date] = t.[Dates]
WHERE t.ID = 4
出现错误:
Msg 4104, Level 16, State 1, Line 2 The multi-part identifier "t.Dates" could not be bound. Msg 4104, Level 16, State 1, Line 2 The multi-part identifier "t.Dates" could not be bound.
预期输出:
给定:ID = 4 和 day=+1
Dates
-----------
2019-12-09
2019-12-10
给定:ID = 4 和 day=+10
Dates
-----------
2019-12-09
2019-12-10
2019-12-11
2019-12-12
2019-12-13
2019-12-14
2019-12-15
2019-12-16
2019-12-17
2019-12-18
给定:ID = 4 和 day=-5
Dates
----------
2019-12-05
2019-12-06
2019-12-07
2019-12-08
2019-12-09
我尝试使用其他格式创建函数
create FUNCTION udf_GetDates(@MinDate DATE,@MaxDate DATE)
RETURNS @_result table (dt date)
AS
begin
insert into @_result
SELECT TOP (DATEDIFF(DAY, @MinDate, @MaxDate) + 1)
Date = DATEADD(DAY, ROW_NUMBER() OVER(ORDER BY a.object_id) - 1, @MinDate)
FROM sys.all_objects a
CROSS JOIN sys.all_objects b;
return
end
和select这样的结果
declare @_date date=(select Dates from tblDates where ID=4)
select *
from udf_GetDates(@_date,DATEADD(day,1,@_date))
我得到了你想要的结果
dt
2019-12-09
2019-12-10
试试这个查询
函数
CREATE FUNCTION udf_GetDates (@StartDate DATE, @Range INT)
RETURNS TABLE
AS
RETURN
SELECT
DATEADD(DAY, nbr - 1, @StartDate) myDate
FROM
(SELECT
ROW_NUMBER() OVER (ORDER BY c.object_id) AS Nbr
FROM
sys.columns c) nbrs
WHERE
nbr - 1 <= @Range
查询用法#1:
SELECT f.myDate
FROM udf_GetDates((SELECT dates FROM tblDates WHERE ID = 4), 2) f
查询用法#2:
SELECT t.*, P.*
FROM tblDates t
OUTER APPLY udf_GetDates(t.Dates, 5) p
WHERE t.ID = 4
更新的答案:
下一个日期
CREATE FUNCTION udf_GetDates (@StartDate DATE, @Range INT)
RETURNS TABLE
AS
RETURN
SELECT
DATEADD(DAY, nbr - 1, @StartDate) myDate
FROM
(SELECT
ROW_NUMBER() OVER (ORDER BY c.object_id) AS Nbr
FROM
sys.columns c) nbrs
WHERE
nbr - 1 <= @Range
以前的日期
CREATE FUNCTION [udf_GetDates_Minuus] (@StartDate DATE, @Range INT)
RETURNS TABLE
AS
RETURN
SELECT
DATEADD(DAY, -(nbr - 1), @StartDate) myDate
FROM
(SELECT
ROW_NUMBER() OVER (ORDER BY c.object_id) AS Nbr
FROM
sys.columns c) nbrs
WHERE
nbr - 1 <= @Range
单个函数中的下一个和上一个日期
CREATE FUNCTION udf_GetDatesNextandPrevious(@StartDate DATE, @Range INT)
RETURNS TABLE
AS
RETURN
SELECT
DATEADD(DAY, nbr - 1, @StartDate) myDate
FROM
(SELECT
ROW_NUMBER() OVER (ORDER BY c.object_id) AS Nbr
FROM
sys.columns c) nbrs
WHERE
nbr - 1 <= @Range
UNION
SELECT
DATEADD(DAY, -(nbr - 1), @StartDate) myDate
FROM
(SELECT
ROW_NUMBER() OVER (ORDER BY c.object_id) AS Nbr
FROM
sys.columns c) nbrs
WHERE
nbr - 1 <= @Range
这 SQL 将 return 两个范围之间的正确日期。只需根据您的需要进行调整即可。
DECLARE @From DATETIME,
@To DATETIME
SELECT @From = '2019-11-13',
@To = '2019-11-19'
;WITH Numbers AS
(
SELECT 0 AS Number
UNION ALL
SELECT Number + 1 AS Number
FROM Numbers
WHERE Number < DATEDIFF(d, @From, @To)
)
SELECT DATEADD(d,
Number, @From) AS Date
FROM Numbers
-- 结果
2019-11-13 00:00:00.000
2019-11-14 00:00:00.000
2019-11-15 00:00:00.000
2019-11-16 00:00:00.000
2019-11-17 00:00:00.000
2019-11-18 00:00:00.000
2019-11-19 00:00:00.000
在 sql 服务器中尝试此代码
DECLARE @selecteddate DATE
DECLARE @day INT = 10
DECLARE @id INT = 4;
DECLARE @count INT = 0;
DECLARE @table1 TABLE
(
date_ DATETIME
)
SELECT @selecteddate = dates
FROM tbldates
WHERE id = @id;
IF( @count <= @day )
BEGIN
if(@day > 1)
begin
set @day = @day - 1
end
WHILE @count <= @day
BEGIN
INSERT INTO @table1
VALUES (Dateadd(day, @count, @selecteddate))
SET @count = @count + 1
END
END
ELSE
BEGIN
WHILE @count > @day
BEGIN
INSERT INTO @table1
VALUES (Dateadd(day, @count, @selecteddate))
SET @count = @count - 1
END
END
SELECT *
FROM @table1
ORDER BY 1