Skip to content
Advertisement

Unexpected NULLs in outer join

I have 3 tables I’m trying to join. Let’s call them TableA, TableB, and TableC:

Here’s some sample data:

TableB and TableC both have foreign keys to TableA via Key1. In practice, TableC can also refer to TableB via Key1 and Key2 combined, if Key2 is not null, but there’s no actual foreign key. Key3 is irrelevant, other than the fact that Key1 and Key2 are not part of the primary key of TableC.

I’m trying to write a query which combines TableB and TableC:

My expectation is that TableB and TableC should both include all their rows, matching up the ones that match on both keys, and NULLS where they don’t match.

I expect to get this:

But instead I get this:

If I comment out the WHERE clause, I get all the rows I expect, except A1 is NULL for the missing rows:

Why is TableA.Key1 coming back NULL and causing it to exclude rows where TableB.Key2 is missing?

EDIT:

Here’s the final fixed query after I learned what I was doing wrong:

Advertisement

Answer

Why is TableA.Key1 coming back NULL and causing it to exclude rows where TableB.Key2 is missing?

A full outer join is the same as an INNER JOIN but any unmatched rows from either side are added back in with NULL for the columns from the other side.

Your query does full outer join of A and C first so start by looking at the result of that.

This returns the following virtual table (VT1) going on to the next stage. As this is the same result as INNER JOIN I doubt it needs any explanation. Every row in @TableC successfully matched the single row in @TableA.

This is then full outer joined onto B. The contents of B are

The INNER JOIN of those two result sets with predicate ON (TableB.Key1 = [A1] AND [C1] IS NULL) OR ([C1] = TableB.Key1 AND [C2] = TableB.Key2) returns only 2 rows.

Unmatched rows from VT1 are added back in as per LEFT JOIN (these are the ones where C3 is 1 or 2)

and unmatched rows from B as per RIGHT JOIN (these were the ones where B2 is 2 or 4)

giving you the final result

User contributions licensed under: CC BY-SA
1 People found this is helpful
Advertisement