Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

T-SQL: Optional table joins?

Let's say I have a stored procedure that will do complicated logic when the parameter @ComplicatedSearch = 1. When it is set to 1, I populate the variable table @ValidIds with valid rows that this procedure can return. When it's 0, the logic is bypassed and we don't need to filter out the rows to return.

So, past that logic, I end up with a statement like so:

SELECT
    m.*
    ,a.*
FROM
    MyTable m
    INNER JOIN AdditionalInfoTable a
       ON m.Id = a.MyTableId
WHERE
   (@ComplicatedSearch = 0 OR EXISTS(SELECT * FROM @ValidIds WHERE Id = m.Id))

This works fine; however, I believe it would be more efficient to join MyTable to @ValidIds when applicable opposed to using EXISTS(), especially when MyTable contains a large number of rows.

Is there any way of doing something like what I have below without writing multiple queries? (the actual query is very large, so having multiple versions with and without joins would not be ideal)

SELECT
    m.*
    ,a.*
FROM
    MyTable m
    ONLY DO THIS IF ComplicatedSearch = 1 PLEASE: INNER JOIN @ValidIds v
       ON m.Id = v.Id
    INNER JOIN AdditionalInfoTable a
       ON m.Id = a.MyTableId
like image 784
John Avatar asked Nov 08 '11 15:11

John


People also ask

Can we join 2 tables without using join?

You can replace the JOIN keyword with a comma in the FROM clause. What do you do next? There's no ON keyword for you to state the joining condition as there would be when using JOIN , e.g., on which two columns you want to join the tables. In this method, you simply use a WHERE clause to do so.

What are the 5 different types of tables joins?

As known, there are five types of join operations: Inner, Left, Right, Full and Cross joins.

What are the 4 types of joins in SQL?

Four types of joins: left, right, inner, and outer.

Can we join tables without condition?

Yes, you can! The longer answer is yes, there are a few ways to combine two tables without a common column, including CROSS JOIN (Cartesian product) and UNION. The latter is technically not a join but can be handy for merging tables in SQL.


1 Answers

Another option:

SELECT
   m.*     
  ,a.*
FROM MyTable m    
 INNER JOIN @ValidIds v
  ON m.Id = case
              when @ComplicatedSearch = 1 then v.Id  --  Filter rows
              else m.Id  --  Select all rows
            end
 INNER JOIN AdditionalInfoTable a    
  ON m.Id = a.MyTableId

You'd need to do performance testing to see if it's efficient enough. Some quick tests showed that (on my data) the same query plan was generated regardless of whether the first call was for complex or not complex.

The "bifurcated" approach (separate procedures) should be most efficient. However, having the same code with just a minor modification in two different places can be a major pain to support, particularly when you have to add subsequent changes to all "instances" of that code. And if the overall size of the data (e.g. overall performance) isn't too great, the "one size mostly fits all" approach might be most effective.

like image 163
Philip Kelley Avatar answered Oct 12 '22 23:10

Philip Kelley