我有一个名为Entries的表来管理特定单位的交易。
在条目中,有一个名为Sales Source的列,用于指定已完成的销售类型。我正在尝试创建一个表格,显示每个单位每个销售来源类型的总收入。
例如:
一个名为AB104的单位收入为8000美元,5000美元来自电话,3000美元来自传真来源。我想显示一个表格,显示同一行中每个销售类型的单位编号和金额。
我尝试了以下查询:
SELECT Unit,
sum(MoneyIN + MoneyOUT) AS Revenue,
sum(VolumeOUT+ VolumeIN) AS volume,
sum(WeightOUT + WeightIN)AS weight,
PercentageR = convert(VARCHAR,convert(MONEY,sum(MoneyIN+MoneyOUT)*100 /
(SELECT sum(MoneyIN + MoneyOUT)
FROM Entries)), 1) + '%',
PercentageV = convert(VARCHAR,convert(MONEY,sum(VolumeIN+VolumeOUT)*100 /
(SELECT sum(VolumeIN + VolumeOUT)
FROM Entries)), 1) + '%',
PercentageW = convert(VARCHAR,convert(MONEY,sum(WeightIN+WeightOUT)*100 /
(SELECT sum(WeightIN + WeightOUT)
FROM Entries)), 1) + '%',
LinkRevenue=
(SELECT sum(MoneyIN+MoneyOUT)
WHERE salesSource ='Link'),
PhoneRevenue=
(SELECT sum(MoneyIN+MoneyOUT)
WHERE salesSource ='Phone'),
EmailRevenue=
(SELECT sum(MoneyIN+MoneyOUT)
WHERE salesSource ='Email'),
FaxRevenue=
(SELECT sum(MoneyIN+MoneyOUT)
WHERE salesSource ='Fax'),
NoneRevenue=
(SELECT sum(MoneyIN+MoneyOUT)
WHERE salesSource ='None')
FROM Entries
GROUP BY Unit,
SalesSource
ORDER BY Unit
然而,该查询的问题在于,它不会在一行中显示每个单元的不同收入类型。此查询将输出:
Unit | rev | vol | weight | % Revenue | % Weight | % Volume | $ Link |$Phone |$Email|$Fax |$None
AB104|5000$|22|15000| 17%| 10%| 15%| 0$|5000$|0$|0$|0$
AB104|3000$|12|18000| 21%| 21%| 7%| 0$|0$|0$|3000$|0$
相反,我希望它将一行中相同单位的所有细节分组,如下所示:
Unit | rev | vol | weight | % Revenue | % Weight | % Volume | $ Link |$Phone |$Email|$Fax |$None
AB104|8000$|34|33000| 38%| 31%| 22%| 0$|5000$|0$|3000$|0$
我怎样才能做到这一点?当我将salesSource从分组中删除时,我收到错误。
答案 0 :(得分:0)
您的分组中有两列。您看到每个SalesSource都有一个Unit行。您可以单独将SalesSource添加为列,并查看。
此外,您希望避免在select子句中添加其他选择,因为您的SQL会针对每个结果运行单独的查询,在您的情况下,对每个结果进行3次查询。这将使您的查询不具有很强的可扩展性。
我认为您需要从group by子句和用例语句中删除SalesSource。
Sum(Case when SalesSource = 'Link' then (MoneyIn+MoneyOut) else 0 end) as LinkRevenue,
您可以使用公用表表达式删除select-in-a-select:
;with totals as (
SELECT sum(WeightIN + WeightOUT) as WeightTotal,
sum(VolumeIN + VolumeOUT) as VolumeTotal,
sum(MoneyIN + MoneyOUT) as MoneyTotal
FROM Entries
)
SELECT Unit,
sum(MoneyIN + MoneyOUT) AS Revenue,
sum(VolumeOUT+ VolumeIN) AS volume,
sum(WeightOUT + WeightIN)AS weight,
PercentageR = convert(VARCHAR,convert(MONEY,sum(MoneyIN+MoneyOUT)*100 /
totals.MoneyTotal), 1) + '%',
PercentageV = convert(VARCHAR,convert(MONEY,sum(VolumeIN+VolumeOUT)*100 /
totals.VolumeTotal), 1) + '%',
PercentageW = convert(VARCHAR,convert(MONEY,sum(WeightIN+WeightOUT)*100 /
totals.WeightTotal), 1) + '%',
Sum(Case when SalesSource = 'Link' then (MoneyIn+MoneyOut) else 0 end) as LinkRevenue,
....
FROM Entries, totals
GROUP BY Unit
ORDER BY Unit
答案 1 :(得分:0)
您可以使用更多cte来清理它,我没有使用$符号格式化Money列,但您可以将其添加到最终选择中
With
--create CTE with money columns summed for the pivotcte
TotalsCTEBySource (Unit, [Revenue], SalesSource) AS
(SELECT Unit, MoneyIn+MoneyOut , SalesSource FROM Entries),
--create CTE with table grand totals for % calcs
GrandTotalsCTE ([Revenue], [Volume],[Weight]) AS
(SELECT sum(MoneyIn+MoneyOut) , sum(VolumeIn+VolumeOut) , sum(WeightIn+WeightOut) FROM Entries),
--create totals by unit cte
TotalsCTEByUnit (Unit, [Revenue], [Volume],[Weight]) AS
(SELECT Unit, sum(MoneyIn+MoneyOut) , sum(VolumeIn+VolumeOut) , sum(WeightIn+WeightOut)
FROM Entries GROUP BY Unit),
--create pivot cte to get the sales source values as column headers, use coalesce() to turn NULL into 0
PivotCTE (Unit, [$ Link],[$ Phone],[$ Fax],[$ Email],[$ None])AS
( select Unit,coalesce(sum([Link]),0), coalesce(sum([Phone]),0),coalesce(sum([Fax]),0),
coalesce(sum([Email]),0),coalesce(sum([None]),0) FROM(
select Unit, [Link],[Phone],[Fax],[Email],[None] from TotalsCTEBySource
PIVOT
(sum(Revenue)FOR SalesSource in ([Link],[Phone],[Fax],[Email],[None])) pivottable
) moneybygroup
group by Unit )
--bring it all together
SELECT t.Unit, t.Revenue, t.Volume, t.Weight,
CONVERT(VARCHAR(50),round(t.Revenue/g.revenue*100,0))+' %' AS [% Revenue],
CONVERT(VARCHAR(50),round(t.Volume/g.Volume*100,0))+' %' AS [% Volume],
CONVERT(VARCHAR(50),round(t.Weight/g.Weight*100,0))+' %' AS [% Weight]
p.[$ Link],p.[$ Phone],p.[$ Fax],p.[$ Email],p.[$ None]
FROM TotalsCTEByUnit t
Join PivotCTE p on t.unit=p.unit
join GrandTotalsCTE g on 1=1