我正在尝试优化SQL查询,但我遇到了一个奇怪的问题。
这是我的优化请求:
SELECT proj.ProjetId AS ProjetId,
SUM (CASE WHEN modTrans.Code != 'FoO' THEN 1 ELSE 0 END) AS VAL1,
SUM(CASE WHEN modTrans.Code = 'Foo' THEN 1 ELSE 0 END) AS VAL2
FROM Projet.Projet proj
INNER JOIN Workflow.PointControle ptCont
ON ptCont.ProjetId = proj.ProjetId
INNER JOIN Workflow.PointControleModele ptContMod
ON ptContMod.PointControleModeleId = ptCont.PointControleModeleId
INNER JOIN Commande.CommandeTAC cdeTAC
ON cdeTAC.ProjetId = proj.ProjetId
INNER JOIN Commande.CommandeTACCatalogue cdeTACCat
ON cdeTACCat.CommandeTACId = cdeTAC.CommandeTACId
INNER JOIN Fournisseur.Fournisseur four
ON four.FournisseurId = cdeTACCat.FournisseurId
INNER JOIN Fournisseur.ModeTransmission modTrans
ON modTrans.ModeTransmissionId = four.ModeTransmissionId
WHERE ptContMod.PointControleModeleCode = 'FFooooooooo'
AND ptCont.Etat = 'Foooooo'
AND proj.DateLivraison IS NOT NULL
AND [proj].[DateLivraison] <= DATEADD(DAY, 14, GETDATE())
GROUP BY proj.ProjetId
HAVING COUNT(VAL1) > 0 AND COUNT(VAL2) = 0
我收到了这个错误:
列名无效:'VAL1'列名无效:'VAL2'
错误发生在HAVING部分。 阅读本文档后,我不明白为什么会出现错误,因为我尊重语法:http://www.w3schools.com/sql/sql_having.asp
您可以在此处找到未经优化的完整请求:
BEGIN
WITH Trans(VAL1, VAL2, projetId) AS
(
SELECT SUM (CASE WHEN modTrans.Code != 'Foo' THEN 1 ELSE 0 END) AS NbNonSALM
, SUM(CASE WHEN modTrans.Code = 'Foo' THEN 1 ELSE 0 END) AS NbSALM
, proj.ProjetId AS projetId
FROM Projet.Projet proj
INNER JOIN Workflow.PointControle ptCont
ON ptCont.ProjetId = proj.ProjetId
INNER JOIN Workflow.PointControleModele ptContMod
ON ptContMod.PointControleModeleId = ptCont.PointControleModeleId
INNER JOIN Commande.CommandeTAC cdeTAC
ON cdeTAC.ProjetId = proj.ProjetId
INNER JOIN Commande.CommandeTACCatalogue cdeTACCat
ON cdeTACCat.CommandeTACId = cdeTAC.CommandeTACId
INNER JOIN Fournisseur.Fournisseur four
ON four.FournisseurId = cdeTACCat.FournisseurId
INNER JOIN Fournisseur.ModeTransmission modTrans
ON modTrans.ModeTransmissionId = four.ModeTransmissionId
WHERE ptContMod.PointControleModeleCode = 'Foooooo'
AND ptCont.Etat = 'Fooo'
AND proj.DateLivraison IS NOT NULL
AND DATEADD(DAY, -14, proj.DateLivraison) <= GETDATE()
GROUP BY proj.ProjetId
)
SELECT proj.ProjetId AS ProjetId
FROM Projet.Projet proj
INNER JOIN Workflow.PointControle ptCont
ON ptCont.ProjetId = proj.ProjetId
INNER JOIN Workflow.PointControleModele ptContMod
ON ptContMod.PointControleModeleId = ptCont.PointControleModeleId
INNER JOIN Commande.CommandeTAC cdeTAC
ON cdeTAC.ProjetId = proj.ProjetId
INNER JOIN Commande.CommandeTACCatalogue cdeTACCat
ON cdeTACCat.CommandeTACId = cdeTAC.CommandeTACId
INNER JOIN Fournisseur.Fournisseur four
ON four.FournisseurId = cdeTACCat.FournisseurId
INNER JOIN Fournisseur.ModeTransmission modTrans
ON modTrans.ModeTransmissionId = four.ModeTransmissionId
INNER JOIN Trans ON Trans.projetId = proj.ProjetId
WHERE ptContMod.PointControleModeleCode = 'Foo'
AND ptCont.Etat = 'Fooo'
AND proj.DateLivraison IS NOT NULL
AND DATEADD(DAY, -14, proj.DateLivraison) <= GETDATE()
GROUP BY proj.ProjetId
HAVING COUNT(trans.NbNonSALM) > 0 AND COUNT(trans.NbSALM) = 0
UNION
SELECT projet.ProjetId AS ProjetId
FROM Projet.Projet projet
INNER JOIN Workflow.PointControle ptControle
ON ptControle.ProjetId = projet.ProjetId
INNER JOIN Workflow.PointControleModele ptContMod
ON ptContMod.PointControleModeleId = ptControle.PointControleModeleId
INNER JOIN Commande.CommandeTAC cdeTAC
ON cdeTAC.ProjetId = projet.ProjetId
INNER JOIN Commande.CommandeTACCatalogue cdeTACCat
ON cdeTACCat.CommandeTACId = cdeTAC.CommandeTACId
INNER JOIN commande.AREntete arEnt
ON arEnt.ProjetIdTAC = cdeTAC.ProjetIdTAC
INNER JOIN Commande.Article art
ON art.AREnteteId = arEnt.AREnteteId AND art.CommandeTACCatalogueId = cdeTACCat.CommandeTACCatalogueId
INNER JOIN Fournisseur.Fournisseur four
ON four.FournisseurId = cdeTACCat.FournisseurId
INNER JOIN Fournisseur.ModeTransmission modTrans
ON modTrans.ModeTransmissionId = four.ModeTransmissionId
WHERE ptContMod.PointControleModeleCode = 'Fooo'
AND ptControle.Etat = 'Foo'
AND arEnt.SuppressionLogique = 0
AND arEnt.Statut IS NOT NULL
AND arEnt.Statut >= 4
AND arEnt.Statut != 9
AND modTrans.Code = 'Fooooooo'
AND projet.SiteId = @siteId
END
;
答案 0 :(得分:1)
您无法在HAVING
子句中使用别名。替换为:
HAVING
SUM(CASE WHEN modTrans.Code != 'FoO' THEN 1 ELSE 0 END) > 0
AND SUM(CASE WHEN modTrans.Code = 'Foo' THEN 1 ELSE 0 END) = 0
答案 1 :(得分:1)
我不是试试这个,但我觉得它对你有用..或者如果出现错误,你可以提供一些样本数据。
;WITH CTE AS
(
SELECT proj.ProjetId AS ProjetId,
SUM (CASE WHEN modTrans.Code != 'FoO' THEN 1 ELSE 0 END) AS VAL1,
SUM(CASE WHEN modTrans.Code = 'Foo' THEN 1 ELSE 0 END) AS VAL2
FROM Projet.Projet proj
INNER JOIN Workflow.PointControle ptCont
ON ptCont.ProjetId = proj.ProjetId
INNER JOIN Workflow.PointControleModele ptContMod
ON ptContMod.PointControleModeleId = ptCont.PointControleModeleId
INNER JOIN Commande.CommandeTAC cdeTAC
ON cdeTAC.ProjetId = proj.ProjetId
INNER JOIN Commande.CommandeTACCatalogue cdeTACCat
ON cdeTACCat.CommandeTACId = cdeTAC.CommandeTACId
INNER JOIN Fournisseur.Fournisseur four
ON four.FournisseurId = cdeTACCat.FournisseurId
INNER JOIN Fournisseur.ModeTransmission modTrans
ON modTrans.ModeTransmissionId = four.ModeTransmissionId
WHERE ptContMod.PointControleModeleCode = 'FFooooooooo'
AND ptCont.Etat = 'Foooooo'
AND proj.DateLivraison IS NOT NULL
AND [proj].[DateLivraison] <= DATEADD(DAY, 14, GETDATE())
GROUP BY proj.ProjetId
)
SELECT ProjetId, VAL1, VAL2
FROM CTE
GROUP BY ProjetId, VAL1, VAL2
HAVING COUNT(VAL1) > 0 AND COUNT(VAL2) = 0
答案 2 :(得分:0)
用此
替换您的HAVING
子句
HAVING
SUM (CASE WHEN modTrans.Code != 'FoO' THEN 1 ELSE 0 END)>0
AND
SUM(CASE WHEN modTrans.Code = 'Foo' THEN 1 ELSE 0 END)=0