SQL查询月/年
我有一个查询,它从表“mesure”中计算每年/每月的值,如下所示SQL查询月/年,sql,sql-server,sql-server-2008-r2,Sql,Sql Server,Sql Server 2008 R2,我有一个查询,它从表“mesure”中计算每年/每月的值,如下所示 select Annee, Mois from ( select annee, Mois -- computing her... round(cast(SUM(nbDates) * 100 as float) / sum(NbDatesTheoriques),2) as DispoBrute ie.... from ( select
select Annee, Mois
from
(
select annee, Mois
-- computing her...
round(cast(SUM(nbDates) * 100 as float) / sum(NbDatesTheoriques),2) as DispoBrute ie....
from (
select
DATEPART(YEAR, DateHeureMesure) as annee,
DATEPART(month, dateheuremesure) as Mois
--TypeMesure,HauteurMesure, count(dateheuremesure) as nbDates,
--SUM(CASE WHEN ValideeMesure = 2 THEN 1 ELSE 0 END) AS NbDatesValides
from mesure
where Id = 378
group by DATEPART(YEAR, DateHeureMesure), DATEPART(month, dateheuremesure)
) req
) req2
group by annee, mois--, mo.MonthNumber
order by annee, mois --min(datedebut)
我简化了查询(删除部分子查询req2/req…),结果是:
Year Month DispoBrute
2013 8 156
2013 9 1254
2013 10 121
2013 11 2121
2013 12 4500
2014 1 155
2014 2 200
2014 3
2014 4
2014 5
好的,但是我怎么能把今年的所有月份都变成这样呢
Year Month DispoBrute
2013 1 NULL
2013 2 NULL
2013 3 NULL
2013 4 NULL
2013 5 NULL
2013 6 NULL
2013 7 NULL
2013 8 156
2013 9 1254
2013 10 121
2013 11 ... ...2121
2013 12 .... ie
2014 1
2014 2
2014 3
2014 4
2014 5
非常感谢 我不完全理解你的目标。但您可以尝试使用下一种方法
declare @start_date datetime = (select min(DateHeureMesure) from measure)
declare @due_date datetime = (select max(DateHeureMesure) from measure)
declare @months as table (
the_year int
, the_month int
)
declare @the_date datetime = @start_date
while @the_date<=@due_date
begin
insert into @months values(datepart(yy, @the_date), datepart(mm, @the_date))
set @the_date = dateadd(mm,1,@the_date)
end
select
m.*
, data.grouping_field1
, data.grouping_field2
, data.agg_value1
, data.agg_value2
from @months m
left join (
select
datepart(yy, m.DateHeureMesure) the_year
, datepart(mm, m.DateHeureMesure) the_month
, m.grouping_field1
, m.grouping_field2
...
, sum(m.agregated_field1) agg_value1
, count(m.agregated_field2) agg_value2
...
from measure m
group by datepart(yy, m.DateHeureMesure)
, datepart(mm, m.DateHeureMesure)
, m.grouping_field1
, m.grouping_field2
) data on data.the_year = m.the_year
and data.the_month = m.the_month
order by m.the_year, m.the_month
“这很有效”,但速度很慢:在临时表上留下年和月的连接:
select the_year, the_month--,NbDatesAvecDonnees,NbDatesTheoriques,NbDatesValides, DispoBrute, DispoValide,dispoBruteCorrigee,dispoValideCorrigee
from @months
left join
(
select Annee, Mois,
min(datedebut) as dtDebutPeriode,
SUM(nbDates) as NbDatesAvecDonnees,
sum(NbDatesTheoriques) as NbDatesTheoriques,sum(NbDatesValides) as NbDatesValides,
round(cast(SUM(nbDates) * 100 as float) / sum(NbDatesTheoriques),2) as DispoBrute,
round(cast(SUM(NbDatesValides) * 100 as float) / sum(NbDatesTheoriques),2) as DispoValide,
case when sum(nbDatesMinMax) != sum(NbDatesTheoriques) then round(cast(SUM(nbDates) * 100 as float) / sum(nbDatesMinMax),2) else round(cast(SUM(nbDates) * 100 as float) / sum(NbDatesTheoriques),2) end as dispoBruteCorrigee,
case when sum(nbDatesMinMax) != sum(NbDatesTheoriques) then round(cast(SUM(NbDatesValides) * 100 as float) / sum(nbDatesMinMax),2) else round(cast(SUM(NbDatesValides) * 100 as float) / sum(NbDatesTheoriques),2) end as dispoValideCorrigee
,case when sum(nbDatesMinMax) != sum(NbDatesTheoriques) then 1 else 0 end as erreur
from (
select
dateMin, dateMax, (DATEDIFF(minute, dateMin, dateMax) + 10)/10 as nbDatesMinMax,
dateDebut, dateadd(second, -1 ,DATEADD(month, 1, datedebut)) as datefin, annee, Mois,
(DATEDIFF(minute, datedebut, dateadd(second, -1 ,DATEADD(month, 1, datedebut))) +10 )/10 as NbDatesTheoriques , nbDates, NbDatesValides
from (
select
min(dateheuremesure) as dateMin,
max(dateheuremesure) as dateMax,
DATEADD(day,-(datepart(day,(DATEADD(hour,-(datepart(hour,dateadd(minute,-(datepart(minute, min(dateHeureMesure))), min(dateheuremesure)))), dateadd(minute,-(datepart(minute, min(dateHeureMesure))), min(dateheuremesure)))))) + 1,
DATEADD(hour,-(datepart(hour,dateadd(minute,-(datepart(minute, min(dateHeureMesure))), min(dateheuremesure)))), dateadd(minute,-(datepart(minute, min(dateHeureMesure))), min(dateheuremesure))))
as dateDebut,
DATEPART(year, DateHeureMesure) as annee,
DATEPART(month, dateheuremesure) as mois, TypeMesure, HauteurMesure,
count(dateheuremesure) as nbDates,
SUM(CASE WHEN ValideeMesure = 2 THEN 1 ELSE 0 END) AS NbDatesValides
from mesure
where IdCampagneMesure = @IdCampagne and DateHeureMesure between @start_date and @due_date
group by DATEPART(YEAR, DateHeureMesure), DATEPART(month, dateheuremesure), TypeMesure , HauteurMesure
) r group by annee, dateMin,dateMax,dateDebut,mois,nbDates,NbDatesValides) r2 group by annee,mois
)
data on data.annee = the_year and data.mois = the_month
使用理货表进行
右连接
(或左连接
,如果从理货表开始),理货表将仅包含数字1-12(月份)。你可以在月数上加入。为什么浮动?数字(7,2)可能是一个更好的选择,因为它是一个精确的数字。浮点数是近似值,并不是每个值都可以存储。为什么会如此复杂?@month表变量不需要年份,它只需要月份,只有1-12个。您可以更轻松地生成。
select the_year, the_month--,NbDatesAvecDonnees,NbDatesTheoriques,NbDatesValides, DispoBrute, DispoValide,dispoBruteCorrigee,dispoValideCorrigee
from @months
left join
(
select Annee, Mois,
min(datedebut) as dtDebutPeriode,
SUM(nbDates) as NbDatesAvecDonnees,
sum(NbDatesTheoriques) as NbDatesTheoriques,sum(NbDatesValides) as NbDatesValides,
round(cast(SUM(nbDates) * 100 as float) / sum(NbDatesTheoriques),2) as DispoBrute,
round(cast(SUM(NbDatesValides) * 100 as float) / sum(NbDatesTheoriques),2) as DispoValide,
case when sum(nbDatesMinMax) != sum(NbDatesTheoriques) then round(cast(SUM(nbDates) * 100 as float) / sum(nbDatesMinMax),2) else round(cast(SUM(nbDates) * 100 as float) / sum(NbDatesTheoriques),2) end as dispoBruteCorrigee,
case when sum(nbDatesMinMax) != sum(NbDatesTheoriques) then round(cast(SUM(NbDatesValides) * 100 as float) / sum(nbDatesMinMax),2) else round(cast(SUM(NbDatesValides) * 100 as float) / sum(NbDatesTheoriques),2) end as dispoValideCorrigee
,case when sum(nbDatesMinMax) != sum(NbDatesTheoriques) then 1 else 0 end as erreur
from (
select
dateMin, dateMax, (DATEDIFF(minute, dateMin, dateMax) + 10)/10 as nbDatesMinMax,
dateDebut, dateadd(second, -1 ,DATEADD(month, 1, datedebut)) as datefin, annee, Mois,
(DATEDIFF(minute, datedebut, dateadd(second, -1 ,DATEADD(month, 1, datedebut))) +10 )/10 as NbDatesTheoriques , nbDates, NbDatesValides
from (
select
min(dateheuremesure) as dateMin,
max(dateheuremesure) as dateMax,
DATEADD(day,-(datepart(day,(DATEADD(hour,-(datepart(hour,dateadd(minute,-(datepart(minute, min(dateHeureMesure))), min(dateheuremesure)))), dateadd(minute,-(datepart(minute, min(dateHeureMesure))), min(dateheuremesure)))))) + 1,
DATEADD(hour,-(datepart(hour,dateadd(minute,-(datepart(minute, min(dateHeureMesure))), min(dateheuremesure)))), dateadd(minute,-(datepart(minute, min(dateHeureMesure))), min(dateheuremesure))))
as dateDebut,
DATEPART(year, DateHeureMesure) as annee,
DATEPART(month, dateheuremesure) as mois, TypeMesure, HauteurMesure,
count(dateheuremesure) as nbDates,
SUM(CASE WHEN ValideeMesure = 2 THEN 1 ELSE 0 END) AS NbDatesValides
from mesure
where IdCampagneMesure = @IdCampagne and DateHeureMesure between @start_date and @due_date
group by DATEPART(YEAR, DateHeureMesure), DATEPART(month, dateheuremesure), TypeMesure , HauteurMesure
) r group by annee, dateMin,dateMax,dateDebut,mois,nbDates,NbDatesValides) r2 group by annee,mois
)
data on data.annee = the_year and data.mois = the_month