2009-09-10 9 views
2

J'essaye de déterminer s'il y a un moyen d'accomplir ceci élégamment. J'ai une requête:Agrégats SQL sans GROUP BY

SELECT TASK.*, PROJCOST.act_cost, PROJCOST.target_cost 
FROM task 
LEFT OUTER JOIN projcost ON task.task_id = projcost.task_id 

Je viens de découvrir que PROJCOST.target_cost et act_cost ne sont pas 1 à 1 et doivent être additionnées. Je comprends comment utiliser SUM et GROUP BY, mais ce que j'essaie de trouver une façon élégante de ne pas avoir à épeler chacun des champs dans la table TASK dans le GROUP BY (il y a près de 100 champs, et oui, j'ai besoin de toutes les colonnes).

Je comprends également que je pourrais déplacer ceci au niveau du code et seulement sélectionner la liste des tâches, puis faire une autre requête pour obtenir les données de coût. J'espérais éviter cela.

En outre, je ne peux pas en faire un proc stocké car ce n'est pas ma base de données.

Des idées?

Merci.

+0

Tout comme aparté: 100 champs est plutôt beaucoup pour une table. Vous pourriez vouloir reconsidérer votre conception de DB ... – sleske

+3

Ce n'est pas ma base de données. Je mentionne cela dans mon message. – billb

Répondre

4
SELECT TASK.*, 
    (select sum (act_cost) from projcost where task_id = task.task_id) as act_cost, 
    (select sum (target_cost) from projcost where task_id = task.task_id) as target_cost 
FROM task 
+0

Génial, merci. – billb

2
SELECT TASK.*, 
IsNull(allprojcosts.total_act_cost, 0) AS total_act_cost, 
IsNull(allprojcosts.total_target_cost, 0) AS total_target_cost 
FROM task 
LEFT OUTER JOIN (SELECT task_id, Sum(act_cost) AS total_act_cost, Sum(target_cost) AS total_target_cost 
    FROM projcost) allprojcosts ON task.task_id = allprojcosts.task_id 
0

Utiliser sous-sélection.

SELECT TASK.*, sums.* 
FROM 
    task left outer join 
    (
    select task.task_id, sum(PROJCOST.act_cost), sum(PROJCOST.target_cost) 
    FROM 
     task LEFT OUTER JOIN 
     projcost ON task.task_id = projcost.task_id 
) sums ON task.task_id = sums.task_id 
0

Pour le bénéfice de tous ceux qui cherchent ceci, fonctions de la fenêtre sont un moyen pratique pour SUM, COUNT, etc., sans avoir besoin de GROUP BY - quand vous autrement obtenir l'erreur:

"... n'est pas valide dans la liste de sélection, car il n'est pas contenu dans soit une fonction d'agrégat, soit la clause GROUP BY."

En utilisant un vide OVER(), les agrégats couvrent l'ensemble des résultats de la requête:

SELECT 
    Col1, 
    Col2, 
    SUM(Col3) OVER() AS SumCol3, 
    COUNT(Col1) OVER() AS NumRows 
FROM Table1