TSQL查询12个月的数据 - 包括没有记录的月份

时间:2017-03-13 19:16:08

标签: sql-server tsql stored-procedures sql-server-2012

我正在尝试为12个月内每个月提交的所有问题创建一个12个月的网格视图。

SELECT 
    YEAR(h.metaInsert) [Year], 
    MONTH(h.metaInsert) [Month], 
    DATENAME(MONTH,h.metaInsert) [Month Name], 
    COUNT(1) [Total Documents]
FROM 
    Document_Count_History AS h
WHERE 
    YEAR(h.metaInsert) = 2017
GROUP BY 
    YEAR(h.metaInsert), MONTH(h.metaInsert), DATENAME(MONTH, h.metaInsert)
ORDER BY 
    1, 2

这样可以完美地返回拥有它的月份的数据,但是对于那个具有该特定月份的0条记录的数据,我没有返回任何数据。

我的目标是查看所有12个月的文件数量。如果没有文档,那个月只会是0,但它将包含在结果集中。

我如何能够拿走我所拥有的并应用失踪的月份?

2 个答案:

答案 0 :(得分:2)

您可以使用类似的内容生成查询的月份序列:

declare @StartDate     date = '20170101'
       ,@NumberOfYears int  = 1;

;with Months as (
select top (12*@NumberOfYears) 
    [Month] = dateadd(Month, row_number() over (order by number) -1, @StartDate)
   , NextMonth = dateadd(Month, row_number() over (order by number), @StartDate)
  from master.dbo.spt_values
)

select 
    year(m.Month) [Year], 
    Month(m.Month) [Month], 
    datename(Month,m.Month) [Month Name], 
    count(h.*) [Total Documents]

from Months as m
  left join Document_Count_History AS h
    on h.metaInsert >= m.Month
   and h.metaInsert < m.NextMonth
--where h.metaInsert >= '20170101'
group by m.Month
order by m.Month

虽然您可能需要考虑添加日历表或日期维度。

日历和数字表格引用:

月份表示例:

create table dbo.Months(
    MonthStart date not null primary key
  , NextMonthStart date not null
  , [Year] smallint not null
  , [Month] tinyint not null
  , [MonthName] varchar(16) not null
);

declare @StartDate     date = '20100101'
       ,@NumberOfYears int  = 30;

insert dbo.Months(MonthStart,NextMonthStart,[Year],[Month])
  select top (12*@NumberOfYears) 
    [MonthStart] = dateadd(month, row_number() over (order by number) -1, @StartDate)
    , NextMonthStart = dateadd(month, row_number() over (order by number), @StartDate)
    , [year] = year(dateadd(month, row_number() over (order by number) -1, @StartDate))
    , [Month] = Month(dateadd(month, row_number() over (order by number) -1, @StartDate))
    , MonthName =  datename(Month,dateadd(month, row_number() over (order by number) -1, @StartDate))
  from master.dbo.spt_values;

,您的查询将简化为:

select 
    m.[Year], 
    m.[Month], 
    m.[MonthName], 
    count(h.*) [Total Documents]
from Months as m
  left join Document_Count_History AS h
    on h.metaInsert >= m.MonthStart
   and h.metaInsert < m.NextMonthStart
where m.Year = 2017
group by m.Month, m.Year, m.MonthName
order by m.MonthStart

答案 1 :(得分:0)

您需要一个日期维度。具体来说,您需要一个包含所有月份值的表格。然后,您可以在获取总计的表上执行左连接,并拉出总和值。