Do You Need a SQL Server Query Hint?

SQL Server has supported the concept of query hints since the earliest version. However, in those versions there was such a small number of hints you could count them with your fingers. Today, if you look at SQL Server’s documentation, there’s not just one page that lists all the hints because there are too many. You can go to the Hints (Transact-SQL) page to see a list of the three different types of hints, but then you have to go to the page for each type of hint to see a list.

So what is a hint? In the English language a hint is a gentle suggestion, but in SQL Server a hint is a directive. A hint tells the SQL Server optimizer what should be in the query plan and the optimizer will do it, unless the hint is impossible to implement. In fact, many people talk about using hints as forcing a query plan.

The optimizer is the component of the SQL Server engine responsible for determining how queries will be processed. The optimizer determines what indexes will be used, the order in which the table will be processed, the kind of join algorithm that will be executed, whether the query will run on multiple processors, etc. It is probably one of the most complex parts of the entire engine. In early versions of SQL Server, the engineers writing the optimizer thought that one day they would have an optimizer that would always come up with the absolute best plan for every query and that hints would no longer be needed. In fact, prior to SQL Server 7, any time I was able to use a hint to come up with a better query plan than the optimizer, the optimizer engineers wanted to know about it. They wanted to try to figure out why the optimizer didn’t come up with that plan without a hint.

For a while it looked like hints would be deprecated as the optimizer became more and more sophisticated, but the opposite actually happened. As more features were added to SQL Server and queries became more and more complex on larger data sets, the optimizer is now so complex and has so many possible plans to investigate there’s no way it could always come up with the best plan. The goal now is to come up with a “good enough plan” without taking more time to optimize than the query will need for execution.  At PASS Summit 2010, Microsoft’s David DeWitt gave a talk entitled “SQL Query Optimization: Why Is It So Hard to Get Right?” describing why the optimizer is so complex. (You can view David’s keynote at www.sqlpass.org/summit/na2010/LiveKeynotes/Thursday.aspx.) Even though more and more hints are added with each version of SQL Server, supporting the fact that the optimizer can’t always come up with the best plan on its own, the documentation page referenced in my first paragraph still includes the following warning:

Caution:

Because the SQL Server query optimizer typically selects the best execution plan for a query, we recommend that <join_hint>, <query_hint>, and <table_hint> be used only as a last resort by experienced developers and database administrators.

As I previously mentioned, hints fall into three categories, which, as you can see in the warning message, the documentation calls join hints, query hints, and table hints. I actually call the second type “option hints” because they’re specified in an OPTION clause at the end of your queries (and I think all hints are query hints).

We obviously don’t have room for any kind of technical discussion of the use cases for the different types of hints, but I’ll give you one technical tidbit about them. There’s a join hint to force a LOOP join and an option hint called LOOP JOIN, and you might be wondering what the difference is. The join hint is specified in the JOIN clause (so you must be using the join specification using the JOIN keyword). When you use a join hint, it applies to only the two tables on either side of the JOIN keyword. If you use LOOP JOIN as an option hint, it applies to all the joins in the query. So you might think that it doesn’t matter whether you use a join hint or an option hint if there are only two tables, but think again. If you use a join hint, it has the side effect of forcing the join order between the tables. In the first query below, in addition to using a LOOP JOIN the optimizer will make sure that SalesOrderHeader is the first table accessed during execution, whereas in the second query, the optimizer can decide for itself which table should be accessed first.

SELECT * <br> FROM sales.SalesOrderheader h INNER LOOP JOIN sales.SalesOrderDetail d<br>   ON h.SalesOrderID = d.SalesOrderDetailID

 

SELECT * <br> FROM sales.SalesOrderheader h JOIN sales.SalesOrderDetail d<p>   ON h.SalesOrderID = d.SalesOrderDetailID<br>OPTION (LOOP JOIN)</p>

Keep in mind that once you have used a hint in your code, you have reduced the value of SQL Server’s optimizer. If the optimizer is upgraded in a service pack, you might never know it. And worse, if your data changes so that the plan forced by your hints is no longer the best plan, you might start getting worse performance than you would have without the hint!

Hints definitely have their place. However, that place should not be at the top of your list of query tuning techniques, it should be much closer to the bottom of the list. Hints can be a solution if you haven’t been able to find any other way to get SQL Server’s optimizer to find an acceptable plan. But take a hint from me and learn all you can about tuning and optimization before you start liberally sprinkling query hints throughout your code.

Discuss this Article 3

pelsql
on Mar 18, 2011
I use LOOP join Hint only when I'm sure that by nature the data accessed by the index is going to be highly selective. I found many times that when the optimizer don't want to use an index specified with the with index hint, that LOOP join does the job. It forces the join order between the two tables using almost all the time the proper index, with the advantage that the INDEX hint could be removed.
You're right saying that LOOP JOIN is a last resort solution. It is better to rewrite the query first, but it happens that some queries are not optimized well by the optimizer, no matter that you update statistics, and check proper type use in search arguments.
Option Hint has its disadvantages too. If your query have many tables, it is not necessarily great to apply a loop join everywhere between all tables of the query. If you force the join type between only two of them it may leave some liberty to the optimizer to arrange the rest.
However forcing the join order between two tables reduces also the liberty of the optimizer beyond just the method of joining the two tables, but you sometimes learn from it.
By wondering why the optimizer don't want to do what you expect from him, when looking at the query plans, you finally find out a missing index somewhere else in the equation that explains that the source of the problem is not between these two tables. You find that what leads to this absurd plan is due to a missing index somewhere else that force the optimizer to takes workarounds. Loop join are sometimes a good diagnostic tool, which help finding the solution to finally remove them from the query.
pelsql
on Mar 18, 2011
The video you mentionned in your link is not available.
pelsql
on Mar 18, 2011
The video you mentionned in your link is not available.

Please or Register to post comments.

IT/Dev Connections

Las Vegas
September 30th - October 4th

Paul ThurottOur Experts will show you:
• Common SQL Server
Problems
• Best Practices for T-SQL
• SQL Server Integration
Services
• Database Development

Come See Michael Otey & Tim Ford in Person!

Early Registration Now Open

From the Blogs
May 21, 2013
blog

A Common Misconception about MAXDOP

Out of the box, SQL Server is (and has been) able to take advantage of multiple processors/cores without any effort on behalf of administrators....More
May 9, 2013
blog

My ISO 8601-Compliant Signature 2

My family recently just "officially" announced that we're in the process of adopting a child from South Africa. We're quite excited, of course, but there's a ton of paperwork to do—along with the need for gobs of signatures....More
May 8, 2013
blog

Use SSIS for ETL from Hadoop

In this blog post, Mark Kromer walks you through using SSIS as a way to use ETL techniques using Microsoft's Hadoop on Windows (HDInsight) as a source using Hive connectors...More
SQL Server Pro Forums

Get answers to questions, share tips, and engage with the SQL Server community in our Forums.