SQL Joins

Posted: May 8th, 2009 | Author: | Filed under: SQL | 4 Comments »

Having spent most of my career working in environments where SQL development and ColdFusion development are handled by separate people or teams. The end result is that my SQL skills are not as evolved as my ColdFusion skills.

At my current job I am the one who writes the SQL for the small and medium-sized ColdFusion & SQL Server-based systems that I develop. Up until the other day I used implicit inner joins and over-used subqueries to get the data that I wanted from a database. My code worked, but it was ugly.

Ah Ha!

My SQL deficiency became apparent as I was sharing some code with a comrade yesterday. I was informed that my code had an “implicitly defined SQL Join”, and was informed that this style of coding is both deprecated and bad form. I was writing my queries like this…

SELECT	c.cheeseId,
	c.name,
	o.name AS 'odorName'
FROM	Cheeses c, Odors o
WHERE	c.odorId = o.odorId

…but as it turns out I should be writing them like this…

SELECT	c.cheeseId,
	c.name,
	o.name AS 'odorName'
FROM	Cheeses c
INNER JOIN
	Odors o ON c.odorId = o.odorId

Both queries will return the same results, but the latter is well formed, and consistent with other join types that you may have in your application.

Once I understood that, a lightbulb appeared over my head. I kicked out a few more code samples to observe the results of left and right joins (a concept that I have been having problems grasping).

Left Joins In The House

SELECT	c.cheeseId,
	c.name,
	o.name AS 'odorName'
FROM	Cheeses c
LEFT JOIN
	Odors o ON c.odorId = o.odorId

The above SQL will return all cheeses and their associated odors. Cheeses that don’t have an odor will also be returned with a null value in the odorName column.

Right Joins In The House

SELECT	c.cheeseId,
	c.name,
	o.name AS 'odorName'
FROM	Cheeses c
RIGHT JOIN
	Odors o ON c.odorId = o.odorId

The above SQL will return all odors and the cheeses that they relate to. Odors that don’t link to an associated cheese will also be returned with a null value in the cheeseId and name columns.

It’s interesting how not understanding one bit of theory or syntax can act as a closed door in your mind that keeps you from understanding a whole world of knowledge. This is why I always maintain an open mind and take a bit of time each day to read other developer’s blogs.


4 Comments on “SQL Joins”

  1. 1 bagar said at 3:33 pm on May 16th, 2009:

    Good explanation.

    It helped me a lot when I thought of joins as Venn Diagrams (overlapping circles). http://en.wikipedia.org/wiki/Venn_diagram The left and right refer to order the tables are listed in.

    If the tables are thought of as partially overlapping circles, the overlaps are where they ‘join’. The key word left and right is saying ‘get all on the left’ or ‘all on the right’, but only the other where they overlap. Thus an inner join gets only the overlap.

    These two queries return identical results (note the order of tables and the corresponding left and right key words):

    select a.col1, b.col2
    from tableA a
    right outer join tableB b
    on b.pkid = a.fkid

    select a.col1, b.col2
    from tableB b
    left outer join tableA a
    on b.pkid = a.fkid

  2. 2 Christopher Vigliotti said at 4:00 pm on May 16th, 2009:

    Thanks for the insight. I guess one person’s right outer join is one personls left outer join!

  3. 3 Russ said at 5:54 pm on May 16th, 2009:

    And if you create an unclustered index on c.odorId, your query performance will increase. Also, you should look into defining foreign keys for database integrity.

  4. 4 Christopher Vigliotti said at 9:24 pm on May 17th, 2009:

    I’m with you on defining foreign keys, check out my more recent post on creating the database that this post references >> http://code.christophervigliotti.com/index.php/2009/05/creating-a-cheesy-database/

    Reading up on “clustered index” vs “unclustered index” now. Feel free to drop me a link or two.


Leave a Reply