0

I have an annoying SQL statement that seem simple but it looks awfull. I want the sql to return a resultset with userdata ordered so that a certain user is the first row in the resultset if that users emailaddress is in the companies table.

I have this SQL that returns what i want but i think it looks awful:

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

And by the way, the emailaddress from the user table can be in many companies so there cant be a join on the emailaddress :-(

Do you have any ideas how to improve that statement?

Im using Microsoft SQL Server 2000.

Edit: Im using this one:

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

Its way more elegant than mine. Thanks Richard L!

1
  • Which RDBMS are you using (Oracle, SQLserver..)
    – FerranB
    Commented Jan 28, 2009 at 12:57

3 Answers 3

6

You could do something like this..

        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
  • 1
    note that this isn't an optimal solution since your select in the case will run once for every returned row. this can potentialy cause a huge performance problem Commented Jan 28, 2009 at 16:07
5

will this work?:

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
1
  • you need to add Users.companyid = Companies.companyid in the JOIN clause
    – devio
    Commented Jan 28, 2009 at 13:33
1

I am not sure this is better, but it is an alternative approach

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

Edit: if there can be many emails across different companies that match, and you are only interested in the given company, this becomes

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

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Not the answer you're looking for? Browse other questions tagged or ask your own question.