我有一個自定義商店網站,當他/她按下購買按鈕時,使用一組規則(更準確地說是7)來爲用戶定位零件。有些規則是這樣的:什麼性能更好:UNION查詢和separete查詢的一堆?
- 查找第一銷售者在同一國家,市,區爲消費者(每區只有一個賣家是允許的)
- 如果賣方上面沒有部分,得到與上述同一組的賣家,並在同一城市
- 如果上述賣家沒有該零件,得到一個賣家在同一城市
- 等等。 。
我已經制定了一個ser並且每個規則的巨大聯盟中有大約300行SQL(格式化爲便於閱讀),只有第一個結果才能找到。
我不確定這是更好的事情要做還是更好地做7順序檢查有條件的往返行程,如果後面的一個在調用下一個結果之前有結果。
我估計大部分用戶都會經歷規則4,即SQL Server的4次往返,只是爲了得到一個部分,並且巨型聯合查詢的結果在不到一秒內返回,少於100,000個部分表。
問題是,如果這個網站開始在可用部件和用戶的溫度下長大,那麼最好是讓SQL Server處理帶有巨大查詢的工作,該查詢只返回我在一次旅行中需要的或者更好調用單獨的查詢?
我們使用傳統的ASP來完成這項工作(是的,老學校,你知道嗎?)如果這在任何情況下都是相關的。
讓我知道你是否需要查看查詢本身。
編輯:
只是爲了總之,這裏是我現在使用的查詢:
SELECT TOP 1 regras.ids, regras.idCadastro, regras.regra, e.descricao AS nomeEstado, cd.descricao AS nomeCidade, b.nome AS nomeBairro
FROM (
SELECT dbo.group_concat(idPecaItem) AS ids, idCadastro, '1' AS regra
FROM (
SELECT TOP 2 idPecaItem, idCadastro
FROM pecasItens
WHERE COALESCE(pecasItens.idCadastro, 0) = (CASE WHEN EXISTS(
SELECT TOP 1 COALESCE(pi.idCadastro, 0)
FROM pecasItens pi
LEFT JOIN cadastros c ON pi.idCadastro = c.idCadastro
WHERE (pi.idCadastro IS NULL OR c.tipoParceiro = 'c') AND idPeca = 31740 AND idPedidoItem IS NULL AND dataEntrada <= '2014-3-13' AND devolucaoSolicitada IS NULL
GROUP BY pi.idCadastro
HAVING COUNT(pi.idPecaItem) >= 2
) THEN (
SELECT TOP 1 COALESCE(pi.idCadastro, 0)
FROM pecasItens pi
LEFT JOIN cadastros c ON pi.idCadastro = c.idCadastro
WHERE (pi.idCadastro IS NULL OR c.tipoParceiro = 'c') AND idPeca = 31740 AND idPedidoItem IS NULL AND dataEntrada <= '2014-3-13' AND devolucaoSolicitada IS NULL
GROUP BY pi.idCadastro
HAVING COUNT(pi.idPecaItem) >= 2
) ELSE NULL END)
AND idPeca = 31740 AND idPedidoItem IS NULL AND dataEntrada <= '2014-3-13' AND devolucaoSolicitada IS NULL
) regra1
GROUP BY idCadastro
UNION
SELECT dbo.group_concat(idPecaItem) AS ids, idCadastro, '2' AS regra
FROM (
SELECT TOP 2 idPecaItem, idCadastro
FROM pecasItens
WHERE COALESCE(pecasItens.idCadastro, 0) = (CASE WHEN EXISTS(
SELECT TOP 1 COALESCE(pi.idCadastro, 0)
FROM pecasItens pi
LEFT JOIN cadastros c ON pi.idCadastro = c.idCadastro AND c.tipoParceiro = 'r' AND c.idCadastroGrupo = 1
WHERE pi.idCadastro IS NOT NULL AND idPeca = 31740 AND idPedidoItem IS NULL AND dataEntrada <= '2014-3-13' AND devolucaoSolicitada IS NULL
GROUP BY pi.idCadastro
HAVING COUNT(pi.idPecaItem) >= 2
) THEN (
SELECT TOP 1 COALESCE(pi.idCadastro, 0)
FROM pecasItens pi
LEFT JOIN cadastros c ON pi.idCadastro = c.idCadastro AND c.tipoParceiro = 'r' AND c.idCadastroGrupo = 1
WHERE pi.idCadastro IS NOT NULL AND idPeca = 31740 AND idPedidoItem IS NULL AND dataEntrada <= '2014-3-13' AND devolucaoSolicitada IS NULL
GROUP BY pi.idCadastro
HAVING COUNT(pi.idPecaItem) >= 2
) ELSE NULL END)
AND idPeca = 31740 AND idPedidoItem IS NULL AND dataEntrada <= '2014-3-13' AND devolucaoSolicitada IS NULL
) regra2
GROUP BY idCadastro
UNION
SELECT dbo.group_concat(idPecaItem) AS ids, idCadastro, '3' AS regra
FROM (
SELECT TOP 2 idPecaItem, idCadastro
FROM pecasItens
WHERE COALESCE(pecasItens.idCadastro, 0) = (CASE WHEN EXISTS(
SELECT TOP 1 COALESCE(pi.idCadastro, 0)
FROM pecasItens pi
LEFT JOIN cadastros c ON pi.idCadastro = c.idCadastro AND c.tipoParceiro = 'r' AND c.idCadastroGrupo = 1
INNER JOIN cadastrosCidades cc ON c.idCadastro = cc.idCadastro AND cc.idCidade = 4850
WHERE pi.idCadastro IS NOT NULL AND idPeca = 31740 AND idPedidoItem IS NULL AND dataEntrada <= '2014-3-13' AND devolucaoSolicitada IS NULL
GROUP BY pi.idCadastro
HAVING COUNT(pi.idPecaItem) >= 2
) THEN (
SELECT TOP 1 COALESCE(pi.idCadastro, 0)
FROM pecasItens pi
LEFT JOIN cadastros c ON pi.idCadastro = c.idCadastro AND c.tipoParceiro = 'r' AND c.idCadastroGrupo = 1
INNER JOIN cadastrosCidades cc ON c.idCadastro = cc.idCadastro AND cc.idCidade = 4850
WHERE pi.idCadastro IS NOT NULL AND idPeca = 31740 AND idPedidoItem IS NULL AND dataEntrada <= '2014-3-13' AND devolucaoSolicitada IS NULL
GROUP BY pi.idCadastro
HAVING COUNT(pi.idPecaItem) >= 2
) ELSE NULL END)
AND idPeca = 31740 AND idPedidoItem IS NULL AND dataEntrada <= '2014-3-13' AND devolucaoSolicitada IS NULL
) regra3
GROUP BY idCadastro
UNION
SELECT dbo.group_concat(idPecaItem) AS ids, idCadastro, '4' AS regra
FROM (
SELECT TOP 2 idPecaItem, idCadastro
FROM pecasItens
WHERE COALESCE(pecasItens.idCadastro, 0) = (CASE WHEN EXISTS(
SELECT TOP 1 COALESCE(pi.idCadastro, 0)
FROM pecasItens pi
INNER JOIN cadastros c ON pi.idCadastro = c.idCadastro AND c.tipoParceiro = 'r'
INNER JOIN cadastrosGrupos cg ON c.idCadastroGrupo = cg.idCadastroGrupo AND cg.idMarca = 2
INNER JOIN cadastrosCidades cc ON c.idCadastro = cc.idCadastro AND cc.idCidade = 4850
WHERE pi.idCadastro IS NOT NULL AND idPeca = 31740 AND idPedidoItem IS NULL AND dataEntrada <= '2014-3-13' AND devolucaoSolicitada IS NULL
GROUP BY pi.idCadastro
HAVING COUNT(pi.idPecaItem) >= 2
) THEN (
SELECT TOP 1 COALESCE(pi.idCadastro, 0)
FROM pecasItens pi
INNER JOIN cadastros c ON pi.idCadastro = c.idCadastro AND c.tipoParceiro = 'r'
INNER JOIN cadastrosGrupos cg ON c.idCadastroGrupo = cg.idCadastroGrupo AND cg.idMarca = 2
INNER JOIN cadastrosCidades cc ON c.idCadastro = cc.idCadastro AND cc.idCidade = 4850
WHERE pi.idCadastro IS NOT NULL AND idPeca = 31740 AND idPedidoItem IS NULL AND dataEntrada <= '2014-3-13' AND devolucaoSolicitada IS NULL
GROUP BY pi.idCadastro
HAVING COUNT(pi.idPecaItem) >= 2
) ELSE NULL END)
AND idPeca = 31740 AND idPedidoItem IS NULL AND dataEntrada <= '2014-3-13' AND devolucaoSolicitada IS NULL
) regra4
GROUP BY idCadastro
UNION
SELECT dbo.group_concat(idPecaItem) AS ids, idCadastro, '5' AS regra
FROM (
SELECT TOP 2 idPecaItem, idCadastro
FROM pecasItens
WHERE COALESCE(pecasItens.idCadastro, 0) = (CASE WHEN EXISTS(
SELECT TOP 1 COALESCE(pi.idCadastro, 0)
FROM pecasItens pi
INNER JOIN cadastrosGrupos cg ON pi.idCadastro = cg.idCadastroMontadora AND cg.idCadastroGrupo = 1
WHERE pi.idCadastro IS NOT NULL AND idPeca = 31740 AND idPedidoItem IS NULL AND dataEntrada <= '2014-3-13' AND devolucaoSolicitada IS NULL
GROUP BY pi.idCadastro
HAVING COUNT(pi.idPecaItem) >= 2
) THEN (
SELECT TOP 1 COALESCE(pi.idCadastro, 0)
FROM pecasItens pi
INNER JOIN cadastrosGrupos cg ON pi.idCadastro = cg.idCadastroMontadora AND cg.idCadastroGrupo = 1
WHERE pi.idCadastro IS NOT NULL AND idPeca = 31740 AND idPedidoItem IS NULL AND dataEntrada <= '2014-3-13' AND devolucaoSolicitada IS NULL
GROUP BY pi.idCadastro
HAVING COUNT(pi.idPecaItem) >= 2
) ELSE NULL END)
AND idPeca = 31740 AND idPedidoItem IS NULL AND dataEntrada <= '2014-3-13' AND devolucaoSolicitada IS NULL
) regra5
GROUP BY idCadastro
UNION
SELECT dbo.group_concat(idPecaItem) AS ids, idCadastro, '6' AS regra
FROM (
SELECT TOP 2 idPecaItem, idCadastro
FROM pecasItens
WHERE COALESCE(pecasItens.idCadastro, 0) = (CASE WHEN EXISTS(
SELECT TOP 1 COALESCE(pi.idCadastro, 0)
FROM pecasItens pi
LEFT JOIN cadastros c ON pi.idCadastro = c.idCadastro AND c.tipoParceiro = 'r' AND c.idEstado = 25 AND c.atendeEstadoTodo = 1
WHERE pi.idCadastro IS NOT NULL AND idPeca = 31740 AND idPedidoItem IS NULL AND dataEntrada <= '2014-3-13' AND devolucaoSolicitada IS NULL
GROUP BY pi.idCadastro
HAVING COUNT(pi.idPecaItem) >= 2
) THEN (
SELECT TOP 1 COALESCE(pi.idCadastro, 0)
FROM pecasItens pi
LEFT JOIN cadastros c ON pi.idCadastro = c.idCadastro AND c.tipoParceiro = 'r' AND c.idEstado = 25 AND c.atendeEstadoTodo = 1
WHERE pi.idCadastro IS NOT NULL AND idPeca = 31740 AND idPedidoItem IS NULL AND dataEntrada <= '2014-3-13' AND devolucaoSolicitada IS NULL
GROUP BY pi.idCadastro
HAVING COUNT(pi.idPecaItem) >= 2
) ELSE NULL END)
AND idPeca = 31740 AND idPedidoItem IS NULL AND dataEntrada <= '2014-3-13' AND devolucaoSolicitada IS NULL
) regra6
GROUP BY idCadastro
UNION
SELECT dbo.group_concat(idPecaItem) AS ids, idCadastro, '7' AS regra
FROM (
SELECT TOP 2 idPecaItem, idCadastro
FROM pecasItens
WHERE COALESCE(pecasItens.idCadastro, 0) = (CASE WHEN EXISTS(
SELECT TOP 1 COALESCE(pi.idCadastro, 0)
FROM pecasItens pi
LEFT JOIN cadastros c ON pi.idCadastro = c.idCadastro AND c.tipoParceiro = 'r' AND c.atendeBrasilTodo = 1
WHERE pi.idCadastro IS NOT NULL AND idPeca = 31740 AND idPedidoItem IS NULL AND dataEntrada <= '2014-3-13' AND devolucaoSolicitada IS NULL
GROUP BY pi.idCadastro
HAVING COUNT(pi.idPecaItem) >= 2
) THEN (
SELECT TOP 1 COALESCE(pi.idCadastro, 0)
FROM pecasItens pi
LEFT JOIN cadastros c ON pi.idCadastro = c.idCadastro AND c.tipoParceiro = 'r' AND c.atendeBrasilTodo = 1
WHERE pi.idCadastro IS NOT NULL AND idPeca = 31740 AND idPedidoItem IS NULL AND dataEntrada <= '2014-3-13' AND devolucaoSolicitada IS NULL
GROUP BY pi.idCadastro
HAVING COUNT(pi.idPecaItem) >= 2
) ELSE NULL END)
AND idPeca = 31740 AND idPedidoItem IS NULL AND dataEntrada <= '2014-3-13' AND devolucaoSolicitada IS NULL
) regra7
GROUP BY idCadastro
) regras
LEFT JOIN cadastros c ON regras.idCadastro = c.idCadastro
LEFT JOIN listaEstados e ON c.idEstado = e.idEstado
LEFT JOIN listaCidades cd ON c.idCidade = cd.idCidade
LEFT JOIN listaBairros b ON c.idBairro = b.idBairro
ORDER BY regra ASC
不,這不是MySQL的。 group_concat()
這裏是來自這個人的自定義聚合http://groupconcat.codeplex.com/
您如何看待,現在是否有必要查看查詢? – Alexander
對不起。我沒有得到它。英語不是我的母語。我想你很諷刺,並告訴我發佈查詢。是對的,有趣嗎? – rcdmk
小心過早優化(「http://c2.com/cgi/wiki?PrematureOptimization」)!但無論如何,不妨考慮一下。以這種方式想想......你有兩個選擇,所以如果它成爲瓶頸,你可以在流程中間切換你的過程。可選性在這裏很好。我傾向於將這些推到一個聯合中,特別是如果底層查詢只能在這種情況下使用。第三種選擇是將過濾的記錄集(Sql很棒)返回到100條左右的記錄,並在代碼中進行決策(並且單元測試您如何做出決定)。 – BlackjacketMack