从组合查询计算TSQL
我目前有六个查询,其中我获取结果并使用电子表格计算两个不同的最终百分比。我相信它可以在一个查询中完成,并且不需要电子表格,但我对SQL的知识还不够丰富,无法理解它。我希望从这里神奇的SQL诸神那里得到一些指导 我们有几个地点,根据其他两个百分比的平均值,计算每个地点的过期百分比和过期沉降百分比: 逾期美元÷预计美元=逾期浮动% 过期单位÷总有效单位=过期单位% 逾期单位%+逾期美元%/2=逾期% Fallout使用相同的计算方法,但着眼于明天的数量 解决:我花时间学习子查询,并通过STID加入其中。感谢所有帮助和指导我的人 方向正确 这是我的最终代码:从组合查询计算TSQL,sql,tsql,Sql,Tsql,我目前有六个查询,其中我获取结果并使用电子表格计算两个不同的最终百分比。我相信它可以在一个查询中完成,并且不需要电子表格,但我对SQL的知识还不够丰富,无法理解它。我希望从这里神奇的SQL诸神那里得到一些指导 我们有几个地点,根据其他两个百分比的平均值,计算每个地点的过期百分比和过期沉降百分比: 逾期美元÷预计美元=逾期浮动% 过期单位÷总有效单位=过期单位% 逾期单位%+逾期美元%/2=逾期% Fallout使用相同的计算方法,但着眼于明天的数量 解决:我花时间学习子查询,并通过STID加入其
SET DATEFIRST 1;
DECLARE @Today date = dbo.getdateparam(92,999);
DECLARE @TodayNum int = DATEPART(dw, @Today);
DECLARE @Saturday date = DATEADD(DAY, (6-@TodayNum)%7, @Today);
DECLARE @PrevSat date = DATEADD(DAY, -7, @Saturday);
Select store.STID As Store,
Proj.ProjRent As Projected,
PDRent.PastDueDollars As PDRent,
UOR.Units As UOR,
PDUnits.UnitsPD As PDUnits,
(PDRent.PastDueDollars / Proj.ProjRent) * 100 As FloatPerc,
(Cast(PDUnits.UnitsPD As Decimal) / Cast(UOR.Units As Decimal)) *
100 As UnitPerc,
Cast(Round((((PDRent.PastDueDollars / Proj.ProjRent) * 100) +
((Cast(PDUnits.UnitsPD As Decimal(18,4)) / Cast(UOR.Units As Decimal(18,4))) *
100)) / 2, 2) As Decimal(18,2)) As PDPerc,
Reds.RedsPD As PDReds,
Round(Cast(Reds.RedsPD As Float) / Cast(UOR.Units As Float) * 100,
2) As RedsPerc
From
-- Stores
(Select Distinct Stores.STID,
Stores.StoreName,
Stores.EMail,
Stores.ManagersName
From Stores
Where Stores.STID Not In (7, 999)) As store
-- Projected Rent
Left Join (Select CashProj.STID,
Sum(CashProj.ProjectedRental) As ProjRent
From CashProj
Where CashProj.ProjectionDate Between DateAdd(mm, DateDiff(mm, 0, @Today),
0) And DateAdd(mm, DateDiff(mm, 0, @Today) + 1, 0)
Group By CashProj.STID) As Proj On store.STID = Proj.STID
-- Past Due Float
Left Join (Select Agreemnt.STID As STID,
Sum(DateDiff(d, Agreemnt.DueDate, (Case DatePart(dw, @Today)
When '1' Then DateAdd(DAY, -7, DateAdd(DAY, (6 - DatePart(dw,
@Today)) % 7, @Today)) When '6' Then @Today
Else DateAdd(DAY, (6 - DatePart(dw, @Today)) % 7, @Today)
End)) * Round(Agreemnt.WeeklyRate / 7, 2)) As PastDueDollars,
DatePart(dw, @Today) As TodayNum,
DateAdd(DAY, -7, DateAdd(DAY, (6 - DatePart(dw, @Today)) % 7,
@Today)) As PrevSat,
DateAdd(DAY, (6 - DatePart(dw, @Today)) % 7, @Today) As Saturday
From Agreemnt
Where Agreemnt.AStatID = 1 And Agreemnt.DueDate < (Case DatePart(dw,
@Today)
When '1' Then DateAdd(DAY, -7, DateAdd(DAY, (6 - DatePart(dw,
@Today)) % 7, @Today)) When '6' Then @Today
Else DateAdd(DAY, (6 - DatePart(dw, @Today)) % 7, @Today)
End) And Agreemnt.RentToRent = 0
Group By Agreemnt.STID) As PDRent On store.STID = PDRent.STID
-- Units On Rent
Left Join (Select Invntry.STID,
Cast(Count(Invntry.StockNumber) As Int) As Units
From Invntry
Inner Join AgreHist On Invntry.InvID = AgreHist.InvID And
Invntry.STID = AgreHist.STID
Inner Join Agreemnt On Agreemnt.STID = AgreHist.STID And
Agreemnt.AgreeID = AgreHist.AgreeID And Agreemnt.AStatID =
AgreHist.AStatID
Where Invntry.InvStatID = 11 And Invntry.DisposalDate Is Null And
Agreemnt.AStatID = 1
Group By Invntry.STID) As UOR On store.STID = UOR.STID
-- Past Due Units
Left Join (Select Invntry.STID,
Cast(Count(Invntry.StockNumber) As Int) As UnitsPD
From Invntry
Inner Join AgreHist On Invntry.InvID = AgreHist.InvID And
Invntry.STID = AgreHist.STID
Inner Join Agreemnt On Agreemnt.STID = AgreHist.STID And
Agreemnt.AgreeID = AgreHist.AgreeID And AgreHist.AStatID =
Agreemnt.AStatID
Where Invntry.InvStatID = 11 And Invntry.DisposalDate Is Null And
Agreemnt.AStatID = 1 And Agreemnt.DueDate < (Case @TodayNum When '1' Then @PrevSat When '6' Then @Today Else @Saturday End) And Agreemnt.RentToRent = 0
Group By Invntry.STID) As PDUnits On store.STID = PDUnits.STID
-- Reds
Left Join (Select Invntry.STID,
Count(Invntry.StockNumber) As RedsPD
From Invntry
Inner Join AgreHist On Invntry.InvID = AgreHist.InvID And
Invntry.STID = AgreHist.STID
Inner Join Agreemnt On Agreemnt.STID = AgreHist.STID And
Agreemnt.AgreeID = AgreHist.AgreeID And Agreemnt.AStatID =
AgreHist.AStatID
Where Invntry.InvStatID = 11 And Invntry.DisposalDate Is Null And
Agreemnt.AStatID = 1 And Agreemnt.DueDate < DateAdd(day, -15, Case
Cast(DatePart(dw, @Today) As Int)
When '1' Then Cast(DateAdd(DAY, -7, DateAdd(DAY, (6 - DatePart(dw,
@Today)) % 7, @Today)) As Date)
When '6' Then Cast(@Today As Date)
Else Cast(DateAdd(DAY, (6 - DatePart(dw, @Today)) % 7, @Today) As
Date) End) And Agreemnt.RentToRent = 0
Group By Invntry.STID) As Reds On store.STID = Reds.STID
Order By Store
您从未将变量设置为任何实际值,而是继续在不相关的select语句中选择无用的变量 在下面的行中
Set @pdD = Sum( Case When a.DueDate < GetDate() Then DateDiff(d,a.DueDate,@runDate) * (a.WeeklyRate/7) )
您没有说明s.DueDate的来源。它甚至不会编译
在这种情况下,选择表是完全不相关的
Select a.STID as STID,
@pdU As PastDueUnits,
@activeU As ActiveUnits,
@pdD As PastDueDollars,
@projRent As ProjRent,
@pdP As PastDuePerc,
@foU As FalloutUnits,
@foD As FalloutDollars,
@foP As FalloutPerc
FROM Agreemnt a INNER JOIN CashProj on a.STID = CashProj.STID JOIN Invntry i ON a.STID = i.STID JOIN AgreHist h On i.InvID = h.InvID And i.STID = h.STID INNER JOIN Agreemnt a On a.STID = h.STID AND a.AgreeID = h.AgreeID AND a.AStatID = h.AStatID
WHERE a.RentToRent = 0 AND i.InvStatID = 11 AND i.DisposalDate IS NULL AND a.AStatID = 1 AND a.DueDate < DateAdd(d, @runDate, GetDate())
GROUP BY a.STID
ORDER BY a.STID
这是一个示例,说明在尝试使用变量进行计算之前应如何设置值
DECLARE @dayNum INT;
SET @dayNum = datepart(dw, getdate());
Select Invntry.STID,
@foU = COUNT(Invntry.StockNumber)
From Invntry
Inner Join AgreHist On Invntry.InvID = AgreHist.InvID And
Invntry.STID = AgreHist.STID
Inner Join Agreemnt On Agreemnt.STID = AgreHist.STID And Agreemnt.AgreeID =
AgreHist.AgreeID And Agreemnt.AStatID = AgreHist.AStatID
Where Invntry.InvStatID = 11 And Invntry.DisposalDate Is Null And
Agreemnt.AStatID = 1 And Agreemnt.DueDate < DateAdd(d, Case @dayNum When '1' Then -2 When '2' Then 1 When '3' Then 1 When '4' Then 1
When '5' Then 1 When '6' Then 0 When '7' Then -1 End, GetDate()) And Agreemnt.RentToRent = 0
Group By Invntry.STID
您不能使用这样的变量,也不能在一个聚合查询中使用,因为它将创建一个巨大的笛卡尔积,并给出错误的结果 您可以对列出的每个查询使用CTE或子查询,然后在STID上将它们连接在一起并应用公式 例如
/* declare all variables here */
DECLARE @dayNum INT;
SET @dayNum = datepart(dw, getdate());
with PastDueDollars as (
select ... from ... group by STID
), ProjectedDollers as (
select ... from ... group by STID
), PastDueUnits as (
select ... from ... group by STID
), preFinal as (
select
PastDueDollarRatio = pdd.PastDueDollars / pd.ProjRent,
PastDueUnitRatio = pdu.UnitsPD / tau.TotalActiveUnits
/* add the other calculations */
from
PastDueDollars pdd
inner join ProjectedDollers pd on pdd.STID = pd.STID
inner join PastDueUnits pdu on pdu.STID = pd.STID
/* join more CTEs */
)
select
f.*,
PastDueRatio = (f.PastDueDollarRatio + f.PastDueUnitRatio) / 2
/* and so on for the other calculations of calculations... */
from
preFinal f
我的问题是缺乏对SQL的知识和理解,我正在改进。这就是我最终得到的结果,它给了我想要的结果,不管是不是最有效的
SET DATEFIRST 1;
DECLARE @Today date = dbo.getdateparam(92,999);
DECLARE @TodayNum int = DATEPART(dw, @Today);
DECLARE @Saturday date = DATEADD(DAY, (6-@TodayNum)%7, @Today);
DECLARE @PrevSat date = DATEADD(DAY, -7, @Saturday);
Select store.STID As Store,
Proj.ProjRent As Projected,
PDRent.PastDueDollars As PDRent,
UOR.Units As UOR,
PDUnits.UnitsPD As PDUnits,
(PDRent.PastDueDollars / Proj.ProjRent) * 100 As FloatPerc,
(Cast(PDUnits.UnitsPD As Decimal) / Cast(UOR.Units As Decimal)) * 100 As UnitPerc,
Cast(Round((((PDRent.PastDueDollars / Proj.ProjRent) * 100) + ((Cast(PDUnits.UnitsPD As Decimal(18,4)) / Cast(UOR.Units As Decimal(18,4))) * 100)) / 2, 2) As Decimal(18,2)) As PDPerc,
Reds.RedsPD As PDReds,
Round(Cast(Reds.RedsPD As Float) / Cast(UOR.Units As Float) * 100,2) As RedsPerc
From
-- Stores
(Select Distinct Stores.STID,
Stores.StoreName,
Stores.EMail,
Stores.ManagersName
From Stores
Where Stores.STID Not In (7, 999)) As store
-- Projected Rent
Left Join (Select CashProj.STID,
Sum(CashProj.ProjectedRental) As ProjRent
From CashProj
Where CashProj.ProjectionDate Between DateAdd(mm, DateDiff(mm, 0, @Today),0) And DateAdd(mm, DateDiff(mm, 0, @Today) + 1, 0)
Group By CashProj.STID) As Proj On store.STID = Proj.STID
-- Past Due Float
Left Join (Select Agreemnt.STID As STID,
Sum(DateDiff(d, Agreemnt.DueDate, (Case DatePart(dw, @Today) When '1' Then DateAdd(DAY, -7, DateAdd(DAY, (6 - DatePart(dw, @Today)) % 7, @Today)) When '6' Then @Today
Else DateAdd(DAY, (6 - DatePart(dw, @Today)) % 7, @Today) End)) * Round(Agreemnt.WeeklyRate / 7, 2)) As PastDueDollars,
DatePart(dw, @Today) As TodayNum,
DateAdd(DAY, -7, DateAdd(DAY, (6 - DatePart(dw, @Today)) % 7,
@Today)) As PrevSat,
DateAdd(DAY, (6 - DatePart(dw, @Today)) % 7, @Today) As Saturday
From Agreemnt
Where Agreemnt.AStatID = 1 And Agreemnt.DueDate < (Case DatePart(dw, @Today) When '1' Then DateAdd(DAY, -7, DateAdd(DAY, (6 - DatePart(dw, @Today)) % 7, @Today)) When '6' Then @Today Else DateAdd(DAY, (6 - DatePart(dw, @Today)) % 7, @Today) End) And Agreemnt.RentToRent = 0
Group By Agreemnt.STID) As PDRent On store.STID = PDRent.STID
-- Units On Rent
Left Join (Select Invntry.STID,
Cast(Count(Invntry.StockNumber) As Int) As Units
From Invntry
Inner Join AgreHist On Invntry.InvID = AgreHist.InvID And
Invntry.STID = AgreHist.STID
Inner Join Agreemnt On Agreemnt.STID = AgreHist.STID And
Agreemnt.AgreeID = AgreHist.AgreeID And Agreemnt.AStatID =
AgreHist.AStatID
Where Invntry.InvStatID = 11 And Invntry.DisposalDate Is Null And Agreemnt.AStatID = 1
Group By Invntry.STID) As UOR On store.STID = UOR.STID
-- Past Due Units
Left Join (Select Invntry.STID,
Cast(Count(Invntry.StockNumber) As Int) As UnitsPD
From Invntry
Inner Join AgreHist On Invntry.InvID = AgreHist.InvID And
Invntry.STID = AgreHist.STID
Inner Join Agreemnt On Agreemnt.STID = AgreHist.STID And
Agreemnt.AgreeID = AgreHist.AgreeID And AgreHist.AStatID =
Agreemnt.AStatID
Where Invntry.InvStatID = 11 And Invntry.DisposalDate Is Null And
Agreemnt.AStatID = 1 And Agreemnt.DueDate < (Case @TodayNum When '1' Then @PrevSat When '6' Then @Today Else @Saturday End) And Agreemnt.RentToRent = 0
Group By Invntry.STID) As PDUnits On store.STID = PDUnits.STID
-- Reds
Left Join (Select Invntry.STID,
Count(Invntry.StockNumber) As RedsPD
From Invntry
Inner Join AgreHist On Invntry.InvID = AgreHist.InvID And Invntry.STID = AgreHist.STID
Inner Join Agreemnt On Agreemnt.STID = AgreHist.STID And Agreemnt.AgreeID = AgreHist.AgreeID And Agreemnt.AStatID = AgreHist.AStatID
Where Invntry.InvStatID = 11 And Invntry.DisposalDate Is Null And Agreemnt.AStatID = 1 And Agreemnt.DueDate < DateAdd(day, -15, Case Cast(DatePart(dw, @Today) As Int) When '1' Then Cast(DateAdd(DAY, -7, DateAdd(DAY, (6 - DatePart(dw, @Today)) % 7, @Today)) As Date) When '6' Then Cast(@Today As Date) Else Cast(DateAdd(DAY, (6 - DatePart(dw, @Today)) % 7, @Today) As Date) End) And Agreemnt.RentToRent = 0
Group By Invntry.STID) As Reds On store.STID = Reds.STID
Order By Store
没有阅读所有这些细节,我有一个简单的问题要问你。在所有这些查询中,表中是否有任何字段列将所有这些查询关联在一起?如果是这样的话,您的答案很简单,您可以使用派生查询连接回所有这些查询。看起来你的结果集说是的有..所以你会选择。。从FirstQuery t1连接选择。。从t2.SomeID=t1.SomeID的第二个查询t2开始,然后从那里继续。@JonH都有一个公共字段Agreemnt.STID,ProjectedDollars除外,ProjectedDollars查询单个表。为了关联表,需要有一些关系,如果您没有关系,您希望sql server如何为您提供此查询…它不能,因为您无法告诉它您想要什么。您需要确定此表如何链接到其他表。@JonH我可以看到合并查询,但不允许我使用结果来计算最终所需的数字。因此,发布您在将查询与预期结果合并时尝试的内容,这是太多的信息。这似乎是我可能需要的,但是,我该如何计算最终的百分比呢?我想我不明白的是,如果我对每个查询使用CTE,并在STID上将它们连接在一起,我该如何从查询结果创建变量,运行计算,然后将查询结果和计算结果一起输出。我只是还没有那一刻…:/@最后你不需要变量。你可以在最终查询的select子句中进行计算。好吧,我想我不明白如何运行四个查询,从这些查询的结果中计算出两个不同的数字,然后从这两个不同的数字的结果中计算出最终的数字。我错过了什么。查询A=结果A,查询B=结果B,查询C=结果C,查询D=结果D,查询E=结果E,查询F=结果F---2。结果A/结果B=第一个数字,结果C/结果D=第二个数字。--3.第一个数字/第二个数字=第一个最终数字。--4.结果E/结果B=第三个数字,结果F/结果D=第四个数字。--5.第三个数字/第四个数字=第二个最终数字。--输出:结果A,结果B,结果C,结果D,第一个决赛,结果E,结果F,第二个决赛由于我缺乏知识。。。如果我这样做,在select语句中使用变量,那么我将不得不运行多个查询?我将如何堆叠它们?要按照@dotjoe建议的方式堆叠它们。您先选择,然后在他的exmaple的最后一个选择中分配。在重新阅读@dotjoe建议后,我想我理解了。但我仍然无法思考的是如何从这些计算中计算出最终的两个百分比并输出数据。