我目前编写了一个小型UDF(表值类型),用于在开始日期和结束日期之间返回table
个日期。已经从另一个表中检索了开始日期和结束日期。
Start_End_Table
WeekNumber | Start Date | End Date
功能:
CREATE FUNCTION [dbo].[DatesBetween](@startDate datetime, @endDate datetime)
RETURNS @dates TABLE (
DateValue datetime NOT NULL
)
AS
BEGIN
WHILE (@startDate <= @endDate) BEGIN
INSERT INTO @dates VALUES (@startDate);
SET @startDate = DATEADD(day, 1, @startDate);
END;
RETURN;
END;
到目前为止,我一直以下列方式使用此功能,
SELECT * FROM [dbo].[DatesBetween](@startDate datetime, @endDate datetime);
继续我需要从Start_End_Date表开始,结束日期并调用该函数。因此,我不认为返回table
是一个选项。如何让这个函数返回一个日期数组而不是一个表?或者还有其他方法可以把它包起来吗?
答案 0 :(得分:2)
尝试CROSS APPLY,因为它将为JOINed表中的每一行运行函数:
SELECT [Date Value]
FROM dbo.Start_End_Table dates
CROSS APPLY [dbo].[DatesBetween](dates.StartDate, dates.EndDate)
WHERE [Week Number]=@WeekNumber;
示例输出类似于开始日期= 2014年1月1日,结束日期= 1/3/2014,@ weeknumber = 1:
| DateValue
1/1/2014
1/2/2014
1/3/2014
修改强>
请尝试以下内联表值函数,因为它会比您的多行TVF快得多,因为:
-
CREATE FUNCTION dbo.GetDates(@StartDate DATETIME, @EndDate DATETIME)
RETURNS TABLE
AS RETURN
WITH cte AS
(
SELECT ROW_NUMBER() OVER (ORDER BY (SELECT NULL)) AS [RowNum]
FROM sys.objects WITH (NOLOCK)
)
SELECT DATEADD(DAY, (cte.[RowNum] - 1), @StartDate) AS [DateValue]
FROM cte
WHERE cte.[RowNum] < (DATEDIFF(DAY, @StartDate, @EndDate) + 2);
GO
SELECT * FROM dbo.GetDates('1/1/2014', '1/3/2014');