如何解决零添加为零
| 该问题已经发布过,但是正确的答案似乎无效,因此我再次询问。 如果没有记录,此代码应返回最近31天,零。 SELECT dates.Date as Dates,isnull(Sum(ElapsedTimeSeconds),0) as ElapsedSeconds
FROM
[fnDateTable] (dateadd(\"m\",-1,CONVERT(VARCHAR(10),GETDATE(),111)),111),\'day\') dates
LEFT JOIN UsersApplog on dates.date = UsersAppLog.LoggedDate
group by Dates.Date
参见[fnDateTable]。
fnDateTable
我得到的只是具有数据的行。很烦人。
谢谢你提供的所有帮助。我敢肯定,这是一个简单的解决方案,但超出了我的范围。
这是一些输出,其中有来自userapplog的数据;
Dates ElapsedSeconds
2011-05-17 00:00:00.000 5854
2011-05-18 00:00:00.000 5864
2011-05-21 00:00:00.000 4758
2011-05-22 00:00:00.000 8434
2011-05-23 00:00:00.000 2162
2011-05-25 00:00:00.000 491
2011-05-26 00:00:00.000 260
2011-05-28 00:00:00.000 216
如果我跑步;
SELECT dates.Date as Dates
FROM
[fnDateTable] (dateadd(\"m\",- 1,\'day\') dates
我懂了
Dates
2011-04-29 00:00:00.000
2011-04-30 00:00:00.000
2011-05-01 00:00:00.000
2011-05-02 00:00:00.000
2011-05-03 00:00:00.000
2011-05-04 00:00:00.000
2011-05-05 00:00:00.000
.
.
解决方法
由于您正在使用SQL Server 2008,因此可以使用using4ѭ和
OUTER APPLY
尝试如下所述的操作。
Common Table Expressions
可用于执行递归函数。在这种情况下,CTE将初始日期作为当前日期之前1个月的日期,然后通过添加1天直到循环到达当前日期来递归循环。因此,形成两个给定日期之间的日期列表。使用该CTE输出,我们可以使用OUTER APPLY
查找给定日期范围内的经过时间总和。
您还可以将CTE创建为表值函数,并按照表值函数一节中的说明使用它。下面提供的两个选项是相同的,并且它们在功能划分方面略有不同。
屏幕截图1显示了存储在表dbo.UsersAppLog中的样本数据,屏幕截图2显示了输出。使用这两种方法的输出将是相同的,因为以下给定选项之间的唯一区别是其中一个选项已将部分逻辑移至函数。
。
Option #1
不使用表值函数的所需输出:
DECLARE @BeginDate DATETIME;
DECLARE @EndDate DATETIME;
SET @BeginDate = DATEADD(MONTH,-1,GETDATE());
SET @EndDate = GETDATE();
WITH CTE(DateRange) AS
(
SELECT @BeginDate AS DateRange
UNION ALL
SELECT DATEADD(DAY,1,DateRange)
FROM CTE
WHERE DATEADD(DAY,DateRange) <= @EndDate
)
SELECT DATEADD(DAY,DATEDIFF(DAY,CTE.DateRange)) AS DateRange,COALESCE(UAL.ElapsedDuration,0) AS ElapsedDuration
FROM CTE
OUTER APPLY (
SELECT SUM(ElapsedSeconds) ElapsedDuration
FROM dbo.UsersAppLog UAL
WHERE DATEDIFF(DAY,UAL.LoggedDate,CTE.DateRange) = 0
) UAL;
Option #2
为表值函数创建脚本:
。
CREATE FUNCTION [dbo].[fntDateRange]
(
@BeginDate DATETIME,@EndDate DATETIME
)
RETURNS TABLE
AS
RETURN
(
WITH CTE(DateRange) AS
(
SELECT @BeginDate AS DateRange
UNION ALL
SELECT DATEADD(DAY,DateRange)
FROM CTE
WHERE DATEADD(DAY,DateRange) <= @EndDate
)
SELECT DATEADD(DAY,CTE.DateRange)) AS DateRange
FROM CTE
)
GO
使用表值函数的所需输出:
。
SELECT RNG.DateRange,0) AS ElapsedDuration
FROM dbo.fntDateRange(DATEADD(MONTH,GETDATE()),GETDATE()) RNG
OUTER APPLY (
SELECT SUM(ElapsedSeconds) ElapsedDuration
FROM dbo.UsersAppLog UAL
WHERE DATEDIFF(DAY,RNG.DateRange) = 0
) UAL;
希望能有所帮助。
屏幕截图1:
屏幕截图2:
版权声明:本文内容由互联网用户自发贡献,该文观点与技术仅代表作者本人。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如发现本站有涉嫌侵权/违法违规的内容, 请发送邮件至 dio@foxmail.com 举报,一经查实,本站将立刻删除。