2010-09-14 15 views
0

J'ai une table avec des colonnes comme celles-ci:requête SQL: SUM sur trois colonnes avec des critères

idx | amount | usercol1 | usercol2 | usercol3 | percentage1 | percentage2 | percentage3 

Les données sont généralement comme ceci:

0 | 1500 | 1  | null  | null  | 100   | null  | null 
1 | 3000 | 2  | 3  | null  | 50   | 50   | null 

Je voudrais faire une SOMME() du montant de chaque utilisateur.

Exemple:

  • user1 = 1500 * 100/100 (quantité * usercol1/100)
  • user2 = 3000 * 50/100 (quantité * usercol1/100)
  • user3 = 3000 * 50/100 (quantité * usercol2/100)

j'ai essayé en vain UNION (ne pas totaliser les sUM).

Existe-t-il un moyen de le faire? Le problème étant qu'il devrait GROUP BY le nom d'utilisateur (que je reçois avec un nom d'utilisateur LEFT OUTER JOIN sur exampletable.usercol1 = usernames.idx). Je sais que c'est non standard et serait mieux avec les relations d'une autre table. Mais je ne suis pas autorisé à changer la structure de la table.

Beaucoup de beaucoup de mercis! : =)

Par la présente, un exemple qui donne un mauvais résultat (semble donner uniquement les résultats de la requête au milieu)

( 
SELECT SUM(projects.amount * (projects.percentage1/100)) as totalproj, 
entities.idx as idx, 
COUNT(projects.idx) as numproj, 
entities.name 
FROM projects 
INNER JOIN entities ON projects.usercol1=entities.idx 
WHERE projects.usercol1=entities.idx 
GROUP BY name ORDER BY totalproj DESC 
) 
UNION ALL 
( 
SELECT SUM(projects.amount * (projects.percentage2/100)) as totalproj, 
entities.idx as idx, 
COUNT(projects.idx) as numproj, 
entities.name 
FROM projects 
INNER JOIN entities ON projects.usercol2=entities.idx 
WHERE projects.usercol2=entities.idx 
GROUP BY name ORDER BY totalproj DESC 
) 
UNION ALL 
( 
SELECT SUM(projects.amount * (projects.percentage3/100)) as totalproj, 
entities.idx as idx, 
COUNT(projects.idx) as numproj, 
entities.name 
FROM projects 
INNER JOIN entities ON projects.usercol3=entities.idx 
WHERE projects.usercol3=entities.idx 
GROUP BY name ORDER BY totalproj DESC 
) 
ORDER BY totalproj DESC 
LIMIT 10 
+0

Impossible de comprendre la question: Je ne comprends pas le travail donné sous "Exemple". usercol1 est diversement 1 ou 2, jamais 100. Aussi, comment usercol1 correspond à l'utilisateur 1 et à l'utilisateur 2, mais usercol2 correspond à l'utilisateur 3? – Hammerite

Répondre

3

Vous pouvez utiliser une table dérivée pour simuler une première table de forme normale puis se joindre à cela.

SELECT SUM(P.amount * (P.percentage/100)) as totalproj, 
     entities.idx as idx, 
     COUNT(P.idx) as numproj, 
     entities.name 
FROM 
(
SELECT idx, amount, usercol1 AS usercol, percentage1 AS percentage 
FROM projects 
UNION ALL 
SELECT idx, amount, usercol2 AS usercol, percentage2 AS percentage 
FROM projects 
UNION ALL 
SELECT idx, amount, usercol3 AS usercol, percentage3 AS percentage 
FROM projects 
) P 
INNER JOIN entities ON P.usercol=entities.idx 
WHERE P.usercol=entities.idx 
GROUP BY name 
ORDER BY totalproj DESC 
+0

Fonctionne comme prévu! – oimoim

+0

Beaucoup de mercis! Vous avez de grandes compétences analytiques! – oimoim

+0

Encore une chose: si j'ajoute un critère ex. : OERE P.country = 2 les résultats SUM sont NULL. Avez-vous une idée pourquoi? – oimoim

1

en utilisant ces données (j'ai ajouté quelques données étranger pour vous assurer que le calcul fonctionnait correctement)

0 1500 1 NULL NULL 100  NULL NULL 
1 3000 2 3  NULL 50  50  NULL 
2 780  4 1  3  70  20  50 
3 3800 2 4  1  30  20  10 

j'ai obtenu ces résultats

user commission 
------- ------------- 
    1  2036 
    2  2640 
    3  1890 
    4  1306 

est ce que vous recherchez ? ci-dessous est ma requête

SELECT [user] 
     ,SUM([commission]) AS commission 
FROM (SELECT [usercol1] AS [user] 
        ,([amount] * [percentage1])/100 AS commission 
      FROM  [dbo].[projects] 
      WHERE  [usercol1] IS NOT NULL 
        AND [percentage1] IS NOT NULL 
      UNION ALL 
      SELECT [usercol2] 
        ,([amount] * [percentage2])/100 
      FROM  [dbo].[projects] 
      WHERE  [usercol2] IS NOT NULL 
        AND [percentage2] IS NOT NULL 
      UNION ALL 
      SELECT [usercol3] 
        ,([amount] * [percentage3])/100 
      FROM  [dbo].[projects] 
      WHERE  [usercol3] IS NOT NULL 
        AND [percentage3] IS NOT NULL 
     ) x 
GROUP BY [user]