1

I'm very sorry to bother with minor problem, but I tried to search old answers for this one and since my skills in SQL are complete 0, I didn't even understand the answers :/! Neither is my English terminology great enough for properly searching.

I have these 2 tables: Cities and Flights.

Cities
+----+-------------+
|id  |    name     |
+----+-------------+
|1   |    Oslo     |
|2   |   New York  |
|3   |   Hong Kong | 
+----+-------------+
Flights
+----+--------------------+-------------------+
|id  |    wherefrom_id    |   whereto_id      |
+----+--------------------+-------------------+
|1   |  3                 |  2                |
|2   |  3                 |  1                |
|3   |  1                 |  3                |
+----+--------------------+-------------------+

Now I have to write code where I need to make city ID's merge to wherefrom_id and whereto_id, in that manner that the answer shows table where you can see list of Flights (FROM/TO). Example:

ANSWER:
+-----------+----------------+
|HONG KONG  |    NEW YORK    |
+-----------+----------------+
|HONG KONG  |    OSLO        |
+-----------+----------------+
|OSLO       |   HONG KONG    |
+-----------+----------------+

This is what I wrote:

SELECT C.name, C.name 
FROM Cities C, Flights F 
WHERE C.id = F.wherefrom_id AND C.id = F.whereto_id;

For some reason this doesnt seem to work and I get nothing showing on my practice program. There is no error or anything it just doesnt show anything on the test answer. I really hope you get what I mean, English is not my first language and I truly tried my best to make it clear as possible :S

HuManatee
  • 67
  • 5

3 Answers3

0

First things first - it's a lot easier to code in standard SQL join syntax. Converting your above to that is

SELECT C.name, C.name 
FROM   Cities C
       INNER JOIN Flights F ON C.id = F.wherefrom_id AND C.id = F.whereto_id;

The question you've been asked requires logic people don't usually use at first so it can be confusing the first time you encounter it.

I will run through the logic jump in a moment.

Imagine your Flights table has the City names in it (not IDs).

  • It would have columns, say, FlightID, From_City_Name, To_City_Name.
  • An example row would be 1, 'Oslo', 'Prague'.

Getting the data for this would be easy e.g., SELECT Flight_ID, From_City_Name, To_City_name FROM Flights.

However, this has many problems. As your question has done, you decide to pull out the cities into their own reference tables.

For this first example, however, you decided to have two extra tables as reference tables: From_City and To_City. These would both have an ID and city name. You then change your Flights to refer to these.

Your code would look like

SELECT F.ID, FC.Name AS From_City, TC.Name AS To_City
FROM   Flights
       INNER JOIN From_City AS FC ON Flights.From_City_ID = FC.ID
       INNER JOIN To_City AS TC ON Flights.To_City_ID = TC.ID

Notice how there are two joins there - one to From_City and one to To_City? That is because the From and To cities are referring to different things in the data.

So, then the final part of the issue: why have two city tables (from and to). Why not have one? Well, you can. If you create just one table, and modify the above, you get something like this:

SELECT F.ID, FC.Name AS From_City, TC.Name AS To_City
FROM   Flights
       INNER JOIN City AS FC ON Flights.From_City_ID = FC.ID
       INNER JOIN City AS TC ON Flights.To_City_ID = TC.ID

Note that all that has changed is that the From_City and To_City references have been pointed to a different table City. However, the rest is the same.

And that, actually, would be your answer. The complex part that most people don't get to straight away, is having two joins to the same table.


As an aside, your original code is technically valid.

SELECT C.name, C.name 
FROM   Cities C
       INNER JOIN Flights F ON C.id = F.wherefrom_id AND C.id = F.whereto_id;

However, what it's effectively saying is to get the city names where the From_City is the same as the To_City - which is obviously not what you want (unless you're looking for turnbacks).

seanb
  • 6,272
  • 2
  • 4
  • 22
  • Thanks for detailed answer! My course material and lessons are made bit funny since we have social distancing going on. I didn't know I had to use JOIN command yet since it was on the next chapter :d. Anyway as I said thanks alot! – HuManatee Oct 13 '20 at 04:11
  • The old way of writing a join was `SELECT * FROM A, B WHERE A.ID = B.ID`. This is the same as `SELECT * FROM A INNER JOIN B ON A.ID = B.ID` (or you could just use 'JOIN' as a shortcut for 'INNER JOIN'. In the answer, it would be `SELECT F.ID, FC.Name AS From_City, TC.Name AS To_City FROM Flights F, City FC, City TC WHERE F.From_City_ID = FC.ID AND F.To_City_ID = TC.ID` – seanb Oct 13 '20 at 04:19
  • Shawnt00's answer was the only one my outdated teaching tool took as right answer, but thanks to your answers I stormed thru all the Join basics xP! – HuManatee Oct 13 '20 at 04:47
  • To be honest the most important part of this (for you) was the logic component. I think it's a strange one to use so early in training. However, the JOIN syntax makes everything a lot easier to write, understand and maintain. – seanb Oct 13 '20 at 04:59
  • Aye aye, sir! Great site we have here. – HuManatee Oct 13 '20 at 05:16
0

What you're doing is an old SQL way of expressing joins. The standard now has better ways to declare the relationships within the from clause and I take it that your material has postponed that slightly:

There are people who will yell at you for using this ancient syntax but the answer is easy enough:

SELECT C1.name, C2.name 
FROM Cities C1, Cities C2, Flights F 
WHERE C1.id = F.wherefrom_id AND C2.id = F.whereto_id

You can think of this as creating a "cross product" of all city-pair combinations and matching up the ones that match actual flights. The key is to references Cities twice by using different aliases (or correlation names.)

shawnt00
  • 16,443
  • 3
  • 17
  • 22
  • I feel so filthy but that was the only answer the program took as correct one :P. The lessons left me hanging in there and didn't mention anything about making multiple references. Tried to do it with the "JOIN" command as seanb suggested earlier but it didn't let me use it on that form. I dunno I feel I missed something important but atleast I learned bunch more xP. – HuManatee Oct 13 '20 at 04:43
  • I *really* hope you changed the select to `SELECT C1.name, C2.name`. If you didn't and your lesson tool took that as the correct answer... well... :( – seanb Oct 13 '20 at 04:57
  • 1
    Haha yea I did! It didn't take it first and it gave me the error, but I have learned from java that you read those errors x). You can't give everything on a silver platter! – HuManatee Oct 13 '20 at 05:09
-1

I think this is what you are looking for..

SELECT wf.name "wherefrom", wt.name "whereto" 
FROM Flights f 
JOIN Cities wf 
ON f.wherefrom_id = wf.id 
JOIN Cities wt 
ON f.whereto_id = wt.id
order by f.id
Bishan
  • 15,211
  • 52
  • 164
  • 258