views:

50

answers:

3

I currently have the following:

Table Town:

  • id
  • name
  • region

Table Supplier:

  • id
  • name
  • town_id

The below query returns the number of suppliers for each town:

SELECT t.id, t.name, count(s.id) as NumSupplier
FROM Town t 
INNER JOIN Suppliers s ON s.town_id = t.id 
GROUP BY t.id, t.name

I now wish to introduce another table in to the query, Supplier_vehicles. A supplier can have many vehicles:

Table Supplier_vehicles:

  • id
  • supplier_id
  • vehicle_id

Now, the NumSupplier field needs to return the number of suppliers for each town that have any of the given vehicle_id (IN condition):

The following query will simply bring back the suppliers that have any of the given vehicle_id:

SELECT * FROM Supplier s, Supplier_vehicles v WHERE s.id = v.supplier_id AND v.vehicle_id IN (1, 4, 6)

I need to integrate this in to the first query so that it returns the number of suppliers that have any of the given vehicle_id.

A: 

If I remember correctly, you can put your second query inside the LEFT OUTER JOIN condition.

So for example, you can do something like

... LEFT OUTER JOIN (SELECT * FROM Suppler s, Supplier_vehicles ......) s ON s.town_id=t.id

In that way you are "integrating" or combining the two queries into one. Let me know if this works.

ebae
Apologies, it is actually an INNER JOIN. And it has not worked I'm afraid.
GSTAR
A: 
SELECT t.name, count(s.id) as NumSupplier
FROM Town t
LEFT OUTER JOIN Suppliers s ON t.id = s.town_id
LEFT OUTER JOIN Supplier_vehicles v ON s.id = v.supplier_id
WHERE v.vehicle_id IN (1,4,6)
GROUP BY t.name
Zane Edward Dockery
If a supplier has more than one vehicle then your query would count the same supplier twice.
Chris Diver
Yes this one doesn't seem to output the correct results.
GSTAR
Also you are reducing the `supplier_vehicles` join to an `INNER JOIN` by filtering on `vehicle_id` in the `WHERE` clause
Chris Diver
+1  A: 
SELECT t.id, t.name, count(s.id) as NumSupplier
FROM Town t 
INNER JOIN Suppliers s ON s.town_id = t.id 
WHERE s.id IN (SELECT sv.supplier_id
               FROM supplier_vehicles sv 
               WHERE sv.vehicle_id IN (1,4,6))
GROUP BY t.id, t.name

Or you could do an INNER JOIN (as your supplier join is INNER, but this will remove towns with no suppliers with those vehicles) and change the COUNT(s.id) TO COUNT(DISTINCT s.id)

Chris Diver
Cheers, this seems to be working fine. Will continue testing.
GSTAR