2009-01-28 13 views
0

J'ai une instruction SQL agaçante qui semble simple mais elle semble horrible. Je veux que le sql renvoie un resultset avec userdata ordonné de sorte qu'un certain utilisateur soit la première ligne dans le resultset si cette adresse email d'utilisateurs est dans la table companies.SQL UNION et ORDER BY

Je cette SQL qui renvoie ce que je veux, mais je pense qu'il est affreux:

select 1 as o, * 
from Users u 
where companyid = 1 
and email = (select email from companies where id=1) 
union 
select 2 as o, * 
from Users u 
where companyid = 1 
and email <> (select email from companies where id=1) 
order by o 

Et en passant, la emailaddress de la table utilisateur peut être dans de nombreuses entreprises donc il ne peux pas être une jointure sur le emailaddress :-(

avez-vous des idées sur la façon d'améliorer cette déclaration

Im en utilisant Microsoft SQL Server 2000.

Edit:? Im en utilisant celui-ci:

select *, case when u.email=(select email from companies where Id=1) then 1 else 2 end AS SortMeFirst 
from Users u 
where u.companyId=1 
order by SortMeFirst 

Sa façon plus élégante que la mienne. Merci Richard L!

+0

Quelle SGBDR utilisez-vous (Oracle, SQL Server ..) – FerranB

Répondre

6

Vous pourriez faire s lya quelque chose comme ça ..

 select CASE 
       WHEN exists (select email from companies c where c.Id = u.ID and c.Email = u.Email) THEN 1 
       ELSE 2 END as SortMeFirst, * 
    From Users u 
    where companyId = 1 
    order by SortMeFirst 
+1

noter que ce n » t une solution optimale puisque votre sélection dans le cas s'exécutera une fois pour chaque ligne retournée. cela peut potentiellement causer un énorme problème de performance –

5

cela fonctionnera ?:

select c.email, * 
from Users u 
    LEFT JOIN companies c on u.email = c.email 
where companyid = 1 
order by c.email desc 
-- order by case when c.email is null then 0 else 1 end 
+0

vous devez ajouter Users.companyid = Companies.companyid dans la clause JOIN – devio

+0

probablement vrai :) –

1

Je ne suis pas sûr que ce soit mieux, mais il est une autre approche

select *, (select count(*) from companies where email = u.email) as o 
from users u 
order by o desc 

Edit: s'il peut y avoir beaucoup d'e-mails entre les différentes entreprises qui correspondent à , et vous êtes seulement intéressé par la compagnie donnée, cela devient

select *, 
(select count(*) from companies c where c.email = u.email and c.id = 1) as o 
from users u 
where companyid = 1 
order by o desc