Reputation: 423
I do not know how to formulate a query. To simplify the problem I have created a silly but simple example. Here are the specifics:
ColorID Color 1 Red 2 Green 3 Blue
Day PantsColorID ShirtColorID 1 2 3 (Day 1 wore green pants and a blue shirt) 2 3 1 (Day 2 wore blue pants and a red shirt)
How do I define a query to return a dataset that looks like:
Day PantsColorID PantsColor ShirtColorID ShirtColor 1 2 Green 3 Blue 2 3 Blue 1 Red
This query gets me close:
select
TableClothes.Day,
TableClothes.PantsColorID,
TableColor.Color as 'color of pants',
TableClothes.ShirtColorID,
TableColor.Color as 'color of shirt',
TableColor.ColorID
from TableClothes, TableColor
where TableClothes.PantsColorID = TableColor.ColorID
Day PantsColorID PantsColor ShirtColorID ShirtColor 1 2 Green 3 Green 2 3 Blue 1 Blue
Of course, this query returns the correct pants color but is shows that same color as the shirt color which is wrong.
How do I construct a query to return the correct color for both pants and shirt?
Thank you.
Upvotes: 0
Views: 544
Reputation: 9532
You need to JOIN the TableClothes table against the Colors table twice, using different conditions and a different alias for the Colors table each time.
SELECT Day,
PantsColorID, PantsColors.Color AS PantsColor,
ShirtColorID, ShirtColors.Color AS ShirtColor
FROM TableClothes
JOIN TableColor PantsColors ON TableClothes.PantsColorID = PantsColors.ColorID
JOIN TableColor ShirtColors ON TableClothes.ShirtColorID = ShirtColors.ColorID
Upvotes: 2
Reputation: 4169
First off. You're using the old style joins which is bad for all of these reasons.
Second, you have identifiers with spaces (not the best choice, you could use underscores instead of spaces) and even worse, you're using single quotes for these identifiers: 'color of pants'
which is not ANSI standard, quite confusing as single quotes are used for string literals and also under deprecation. See another set of good reasons. So, it's better to use double quotes (or brackets) for identifiers: "color of pants"
.
Third, we'll add the statement separator (;
) because it should be obvious where a statement ends and also because SQL-Server while being happy to allow you not place these separators and do the dirty job of finding out where a statements ends and another starts, it will get confused when the next statement starts with WITH
. Help him (and the next developer who will be reading your code) to stay sane.
So if we fix those, your query will look like this:
select
TableClothes.Day,
TableClothes.PantsColorID,
TableColor.Color as "color of pants",
TableClothes.ShirtColorID,
TableColor.Color as "color of shirt",
TableColor.ColorID
from TableClothes
inner join TableColor
on TableClothes.PantsColorID = TableColor.ColorID ;
The reason this isn't giving you the results you crave is you also need to join to both the shirt and pants colorID that way you can get the descriptor information for both.
select
TableClothes.Day,
TableClothes.PantsColorID,
TableColor.Color as "color of pants",
TableClothes.ShirtColorID,
TableColor.Color as "color of shirt",
TableColor.ColorID
from TableClothes
inner join TableColor
on TableClothes.PantsColorID = TableColor.ColorID
inner join TableColor
on TableClothes.ShirtColorID = TableColor.ColorID
Oh but wait that doesn't compile. That's because when you refer to TableColor twice like this the Database System has no clue which one you are referring to in your SELECT
and JOIN
statements. So we're going to use a technique called aliasing that will not only solve for this but make your code easier to read.
select
C.Day,
C.PantsColorID,
P.Color as 'color of pants',
C.ShirtColorID,
S.Color as 'color of shirt',
C.ColorID
from TableClothes as C
inner join TableColor as P
on C.PantsColorID = P.ColorID
inner join TableColor as S
on C.ShirtColorID = S.ColorID ;
There now we have a functional clean easy to read query.
Upvotes: 7
Reputation: 70538
You use an alias -- like this:
select TableClothes.Day,
TableClothes.PantsColorID,
Color1.Color as 'color of pants' ,
TableClothes.ShirtColorID,
Color2.Color as 'color of shirt',
from TableClothes, TableColor as Color1, TableColor as Color2
where TableClothes.PantsColorID = Color1.ColorID
and TableClothes.ShirtColorID = Color2.ColorID
More common to use modern join syntax (which I think makes it clearer)
select TableClothes.Day,
TableClothes.PantsColorID,
TableColor.Color as 'color of pants' ,
TableClothes.ShirtColorID,
Color2.Color as 'color of shirt',
from TableClothes,
join TableColor as Color1 on TableClothes.PantsColorID = Color1.ColorID
join TableColor as Color2 on TableClothes.ShirtColorID = Color2.ColorID
Upvotes: 4
Reputation: 2738
You need to join the Clothes table to the Color table twice. Like
select * from TableClothes L, TableColor C1, TableColor C2 where
L.shirtcolorid = c1.colorid and L.pantscolorid = c2.colorid
Upvotes: -2
Reputation: 1631
SELECT TableClothes.Day,
TableClothes.PantsColorID,
t1.Color as PantsColor ,
TableClothes.ShirtColorID,
t2.Color as ShirtColor,
TableColor.ColorID
from TableClothes
LEFT JOIN TableColor as t1
ON TableColor.ColorId = TableClothes.PantsColorID
LEFT JOIN TableColor as t2
ON TableColor.ColorId = TableClothes.ShirtColorID
Upvotes: -2