<?xml version="1.0" encoding="UTF-8"?><rss version="2.0"
	xmlns:content="http://purl.org/rss/1.0/modules/content/"
	xmlns:dc="http://purl.org/dc/elements/1.1/"
	xmlns:atom="http://www.w3.org/2005/Atom"
	xmlns:sy="http://purl.org/rss/1.0/modules/syndication/"
		>
<channel>
	<title>Comments on: Good SQL Querying</title>
	<atom:link href="http://www.pythian.com/news/1116/good-sql-querying/feed/" rel="self" type="application/rss+xml" />
	<link>http://www.pythian.com/news/1116/good-sql-querying/</link>
	<description>News and views from Pythian DBAs</description>
	<lastBuildDate>Fri, 10 Feb 2012 13:01:25 +0000</lastBuildDate>
	<sy:updatePeriod>hourly</sy:updatePeriod>
	<sy:updateFrequency>1</sy:updateFrequency>
	<generator>http://wordpress.org/?v=3.0.4</generator>
	<item>
		<title>By: Gints Plivna</title>
		<link>http://www.pythian.com/news/1116/good-sql-querying/#comment-237304</link>
		<dc:creator>Gints Plivna</dc:creator>
		<pubDate>Wed, 16 Jul 2008 07:01:48 +0000</pubDate>
		<guid isPermaLink="false">http://www.pythian.com/blogs/1116/good-sql-querying#comment-237304</guid>
		<description>I&#039;ve tried to summarize various join types here http://www.gplivna.eu/papers/sql_join_types.htm
I&#039;d like to add that natural join syntax is very dangerous and actaully asks for trouble as soon as table structure changes.
Speaking about join criteria vs filter criteria - it doesn&#039;t really matter for inner joins where these are written. However for outer joins it really does matter where another criteria are written - result changes - see chapter 6.4 Difference between predicates in ON clause vs. predicates in WHERE clause in my article.
And speaking cross join vs inner join - the biggest problem is that MySQL had mixed them up, and historically cannot probably so easy enforce cross join like real cartesian join raising error when on clause is applied and inner join like normal inner join. I think the situation is the same like old outer join operators in Oracle (+) or MS SQL (*= and =*).
And speaking about explicit JOIN keyword or putting tables in where clause - there are benefits for both approaches and both approaches are according to standard, so I personally think that&#039;s the matter of each project - whether they like one or another syntactic type. That&#039;s more matter of taste :)</description>
		<content:encoded><![CDATA[<p>I&#8217;ve tried to summarize various join types here <a href="http://www.gplivna.eu/papers/sql_join_types.htm" rel="nofollow">http://www.gplivna.eu/papers/sql_join_types.htm</a><br />
I&#8217;d like to add that natural join syntax is very dangerous and actaully asks for trouble as soon as table structure changes.<br />
Speaking about join criteria vs filter criteria &#8211; it doesn&#8217;t really matter for inner joins where these are written. However for outer joins it really does matter where another criteria are written &#8211; result changes &#8211; see chapter 6.4 Difference between predicates in ON clause vs. predicates in WHERE clause in my article.<br />
And speaking cross join vs inner join &#8211; the biggest problem is that MySQL had mixed them up, and historically cannot probably so easy enforce cross join like real cartesian join raising error when on clause is applied and inner join like normal inner join. I think the situation is the same like old outer join operators in Oracle (+) or MS SQL (*= and =*).<br />
And speaking about explicit JOIN keyword or putting tables in where clause &#8211; there are benefits for both approaches and both approaches are according to standard, so I personally think that&#8217;s the matter of each project &#8211; whether they like one or another syntactic type. That&#8217;s more matter of taste :)</p>
]]></content:encoded>
	</item>
	<item>
		<title>By: Toby</title>
		<link>http://www.pythian.com/news/1116/good-sql-querying/#comment-234990</link>
		<dc:creator>Toby</dc:creator>
		<pubDate>Sat, 12 Jul 2008 13:40:19 +0000</pubDate>
		<guid isPermaLink="false">http://www.pythian.com/blogs/1116/good-sql-querying#comment-234990</guid>
		<description>Nitpicks: &quot;performant&quot; in your first line has a typo; but it&#039;s an ugly word, what about &quot;faster&quot;? Also &quot;criteria&quot; is plural, so &quot;criteria where it belongs&quot; and other cases are incorrect.</description>
		<content:encoded><![CDATA[<p>Nitpicks: &#8220;performant&#8221; in your first line has a typo; but it&#8217;s an ugly word, what about &#8220;faster&#8221;? Also &#8220;criteria&#8221; is plural, so &#8220;criteria where it belongs&#8221; and other cases are incorrect.</p>
]]></content:encoded>
	</item>
	<item>
		<title>By: rudy</title>
		<link>http://www.pythian.com/news/1116/good-sql-querying/#comment-234780</link>
		<dc:creator>rudy</dc:creator>
		<pubDate>Sat, 12 Jul 2008 02:10:34 +0000</pubDate>
		<guid isPermaLink="false">http://www.pythian.com/blogs/1116/good-sql-querying#comment-234780</guid>
		<description>thanks sheeri

maybe some day i can also make you see the benefit of qualifying all columns in join queries -- after all, you&#039;re not doing it for yourself, you&#039;re doing it for whoever has to maintain the query later, eh

;o)</description>
		<content:encoded><![CDATA[<p>thanks sheeri</p>
<p>maybe some day i can also make you see the benefit of qualifying all columns in join queries &#8212; after all, you&#8217;re not doing it for yourself, you&#8217;re doing it for whoever has to maintain the query later, eh</p>
<p>;o)</p>
]]></content:encoded>
	</item>
	<item>
		<title>By: Sheeri Cabral</title>
		<link>http://www.pythian.com/news/1116/good-sql-querying/#comment-234473</link>
		<dc:creator>Sheeri Cabral</dc:creator>
		<pubDate>Fri, 11 Jul 2008 13:20:13 +0000</pubDate>
		<guid isPermaLink="false">http://www.pythian.com/blogs/1116/good-sql-querying#comment-234473</guid>
		<description>Rudy, you&#039;re absolutely correct, my apologies.  The filtering queries will make it act like an INNER JOIN.  This is a great example of debugging too -- you can see, because I wrote LEFT JOIN, that I intended a LEFT JOIN, so you can see my mistake.  The filters such as WHERE amount&gt;500 should be moved to the join criteria in the FROM claus.</description>
		<content:encoded><![CDATA[<p>Rudy, you&#8217;re absolutely correct, my apologies.  The filtering queries will make it act like an INNER JOIN.  This is a great example of debugging too &#8212; you can see, because I wrote LEFT JOIN, that I intended a LEFT JOIN, so you can see my mistake.  The filters such as WHERE amount>500 should be moved to the join criteria in the FROM claus.</p>
]]></content:encoded>
	</item>
	<item>
		<title>By: Rishi Agarwal</title>
		<link>http://www.pythian.com/news/1116/good-sql-querying/#comment-234399</link>
		<dc:creator>Rishi Agarwal</dc:creator>
		<pubDate>Fri, 11 Jul 2008 11:54:13 +0000</pubDate>
		<guid isPermaLink="false">http://www.pythian.com/blogs/1116/good-sql-querying#comment-234399</guid>
		<description>Hi, Nice post. Completely agree with you on the part about &quot; join criteria vs. filter criteria &quot;. Thats the main reason I shifted from using &quot;comma joins&quot; to &quot; left/right/inner join&quot; and this has changed the way I think and write queries.</description>
		<content:encoded><![CDATA[<p>Hi, Nice post. Completely agree with you on the part about &#8221; join criteria vs. filter criteria &#8220;. Thats the main reason I shifted from using &#8220;comma joins&#8221; to &#8221; left/right/inner join&#8221; and this has changed the way I think and write queries.</p>
]]></content:encoded>
	</item>
	<item>
		<title>By: Roland Bouman</title>
		<link>http://www.pythian.com/news/1116/good-sql-querying/#comment-234243</link>
		<dc:creator>Roland Bouman</dc:creator>
		<pubDate>Fri, 11 Jul 2008 08:14:20 +0000</pubDate>
		<guid isPermaLink="false">http://www.pythian.com/blogs/1116/good-sql-querying#comment-234243</guid>
		<description>Hi Sheeri!

nice post. Few comments:

&quot;There is no such thing as a â€œcomma joinâ€, really what you mean is an â€œinner joinâ€ or a â€œleft/right joinâ€ or â€œcross joinâ€ (or â€œnatural joinâ€).&quot;

This suggests that NATURAL JOIN is a proper type. It is not, you can have inner and outer NATURAL joins. I don&#039;t regard LEFT/RIGHT as different types either - it&#039;s just syntax, there is not difference in the concept. So, I end up with three proper join types: cross join, inner join, outer join. (I don&#039;t write caps now because I&#039;m referring to the concepts - not the actual syntax).

One of the things I expected you&#039;d write about is LEFT vs RIGHT joins. Personally I always only use LEFT - never RIGHT. It doesn&#039;t really matter which one you use but I really don&#039;t see the point of using both. 

&quot;Now, an example where it really helped me to debug when the query was written in â€œgoodâ€ format (note that this no longer uses the sakila sample database):&quot;

In MySQL 5.1 and MySQL 5.0 you get a syntax error when you leave out the ON clause for LEFT and RIGHT join (insanely enough, not for INNER JOIN). So I don&#039;t see what how the formatting could&#039;ve helped there.

Your remark about &quot;join criteria&quot; vs &quot;filter criteria&quot; is nice and I tend to think about it that way too. That is to say, I used to call all conditions that relate tables by comparing their columns as the &#039;join condition&#039;. It turns out you can&#039;t really rigorously define it.
consider 

SELECT City.Name, Country.Name, Country.IndepYear
FROM   City LEFT JOIN Country
ON     City.ID = Country.Capital
AND    Country.IndepYear IS NOT NULL
WHERE  City.Name IN (&#039;Kabul&#039;, &#039;Oranjestad&#039;, &#039;Qandahar&#039;)

(â€œall cities, and if they are the capital of an independent country, the country name and year of independenceâ€)

Here &quot;Country.IndepYear IS NOT NULL&quot; does not realy relate a city to a country, it is more like an extra condition to be applied when matching capital cities to their country. We can&#039;t move it to the WHERE clause, as that would change the meaning of the query (effectively turning it into an inner join of &quot;all capital cities of independent countries&quot;)

So, what are we to call this &quot;Country.IndepYear IS NOT NULL&quot; part? The only sensible thing I can think of is to call the entire thing

City.ID = Country.Capital AND Country.IndepYear IS NOT NULL

the join condition, and not make any judgment of the nature of the expression.

(although I still feel that for inner joins it is best to keep the &#039;filtering&#039; ones separate from the &#039;join&#039; ones, but it&#039;s just a habit.)

kind regards,

Roland</description>
		<content:encoded><![CDATA[<p>Hi Sheeri!</p>
<p>nice post. Few comments:</p>
<p>&#8220;There is no such thing as a â€œcomma joinâ€, really what you mean is an â€œinner joinâ€ or a â€œleft/right joinâ€ or â€œcross joinâ€ (or â€œnatural joinâ€).&#8221;</p>
<p>This suggests that NATURAL JOIN is a proper type. It is not, you can have inner and outer NATURAL joins. I don&#8217;t regard LEFT/RIGHT as different types either &#8211; it&#8217;s just syntax, there is not difference in the concept. So, I end up with three proper join types: cross join, inner join, outer join. (I don&#8217;t write caps now because I&#8217;m referring to the concepts &#8211; not the actual syntax).</p>
<p>One of the things I expected you&#8217;d write about is LEFT vs RIGHT joins. Personally I always only use LEFT &#8211; never RIGHT. It doesn&#8217;t really matter which one you use but I really don&#8217;t see the point of using both. </p>
<p>&#8220;Now, an example where it really helped me to debug when the query was written in â€œgoodâ€ format (note that this no longer uses the sakila sample database):&#8221;</p>
<p>In MySQL 5.1 and MySQL 5.0 you get a syntax error when you leave out the ON clause for LEFT and RIGHT join (insanely enough, not for INNER JOIN). So I don&#8217;t see what how the formatting could&#8217;ve helped there.</p>
<p>Your remark about &#8220;join criteria&#8221; vs &#8220;filter criteria&#8221; is nice and I tend to think about it that way too. That is to say, I used to call all conditions that relate tables by comparing their columns as the &#8216;join condition&#8217;. It turns out you can&#8217;t really rigorously define it.<br />
consider </p>
<p>SELECT City.Name, Country.Name, Country.IndepYear<br />
FROM   City LEFT JOIN Country<br />
ON     City.ID = Country.Capital<br />
AND    Country.IndepYear IS NOT NULL<br />
WHERE  City.Name IN (&#8216;Kabul&#8217;, &#8216;Oranjestad&#8217;, &#8216;Qandahar&#8217;)</p>
<p>(â€œall cities, and if they are the capital of an independent country, the country name and year of independenceâ€)</p>
<p>Here &#8220;Country.IndepYear IS NOT NULL&#8221; does not realy relate a city to a country, it is more like an extra condition to be applied when matching capital cities to their country. We can&#8217;t move it to the WHERE clause, as that would change the meaning of the query (effectively turning it into an inner join of &#8220;all capital cities of independent countries&#8221;)</p>
<p>So, what are we to call this &#8220;Country.IndepYear IS NOT NULL&#8221; part? The only sensible thing I can think of is to call the entire thing</p>
<p>City.ID = Country.Capital AND Country.IndepYear IS NOT NULL</p>
<p>the join condition, and not make any judgment of the nature of the expression.</p>
<p>(although I still feel that for inner joins it is best to keep the &#8216;filtering&#8217; ones separate from the &#8216;join&#8217; ones, but it&#8217;s just a habit.)</p>
<p>kind regards,</p>
<p>Roland</p>
]]></content:encoded>
	</item>
	<item>
		<title>By: Carsten Pedersen</title>
		<link>http://www.pythian.com/news/1116/good-sql-querying/#comment-234239</link>
		<dc:creator>Carsten Pedersen</dc:creator>
		<pubDate>Fri, 11 Jul 2008 08:02:26 +0000</pubDate>
		<guid isPermaLink="false">http://www.pythian.com/blogs/1116/good-sql-querying#comment-234239</guid>
		<description>Great post Sheeri, and the number of comments certainly shows that you hit a nerve :-)

Agree with everything you say, and very happy that you also took time to mention USING .. way too many people are unaware of just how powerful that is, not only when writing it but also in helping someone understand what&#039;s going on when they read the query 6 months from now.

My personal addition would be a rant about those people that insist on aliasing every single table and column with a shorthand name, because &quot;it makes it easier to understand and write&quot;.</description>
		<content:encoded><![CDATA[<p>Great post Sheeri, and the number of comments certainly shows that you hit a nerve :-)</p>
<p>Agree with everything you say, and very happy that you also took time to mention USING .. way too many people are unaware of just how powerful that is, not only when writing it but also in helping someone understand what&#8217;s going on when they read the query 6 months from now.</p>
<p>My personal addition would be a rant about those people that insist on aliasing every single table and column with a shorthand name, because &#8220;it makes it easier to understand and write&#8221;.</p>
]]></content:encoded>
	</item>
	<item>
		<title>By: Arjen Lentz</title>
		<link>http://www.pythian.com/news/1116/good-sql-querying/#comment-233953</link>
		<dc:creator>Arjen Lentz</dc:creator>
		<pubDate>Fri, 11 Jul 2008 01:18:34 +0000</pubDate>
		<guid isPermaLink="false">http://www.pythian.com/blogs/1116/good-sql-querying#comment-233953</guid>
		<description>And for optimum evil, try NATURAL [INNER&#124;LEFT&#124;RIGHT] JOIN.
Unless there is a very strict and sane identifier naming rule in place with the schema design, it&#039;ll break things in oh so many ways at a future time you won&#039;t expect ;-)</description>
		<content:encoded><![CDATA[<p>And for optimum evil, try NATURAL [INNER|LEFT|RIGHT] JOIN.<br />
Unless there is a very strict and sane identifier naming rule in place with the schema design, it&#8217;ll break things in oh so many ways at a future time you won&#8217;t expect ;-)</p>
]]></content:encoded>
	</item>
	<item>
		<title>By: rudy</title>
		<link>http://www.pythian.com/news/1116/good-sql-querying/#comment-233938</link>
		<dc:creator>rudy</dc:creator>
		<pubDate>Fri, 11 Jul 2008 00:31:23 +0000</pubDate>
		<guid isPermaLink="false">http://www.pythian.com/blogs/1116/good-sql-querying#comment-233938</guid>
		<description>if, for a specific day, there is no matched row in the sales table, then the columns in the intermediate result produced by the LEFT OUTER JOIN that would&#039;ve come from the sales table will be NULL, right?  i mean, that&#039;s how a LEFT OUTER JOIN works

so what happens in the WHERE clause?  one of those columns has to be greater than 500, and another of those columns has to be equal to &#039;paid&#039;

NULL is not greater than anything, and NULL is not equal to anything

therefore, all the unmatched rows will be filtered out

in effect, it&#039;s an inner join

unless, of course, &quot;amount&quot; and &quot;type&quot; are actually in the day_tbl   ;o)</description>
		<content:encoded><![CDATA[<p>if, for a specific day, there is no matched row in the sales table, then the columns in the intermediate result produced by the LEFT OUTER JOIN that would&#8217;ve come from the sales table will be NULL, right?  i mean, that&#8217;s how a LEFT OUTER JOIN works</p>
<p>so what happens in the WHERE clause?  one of those columns has to be greater than 500, and another of those columns has to be equal to &#8216;paid&#8217;</p>
<p>NULL is not greater than anything, and NULL is not equal to anything</p>
<p>therefore, all the unmatched rows will be filtered out</p>
<p>in effect, it&#8217;s an inner join</p>
<p>unless, of course, &#8220;amount&#8221; and &#8220;type&#8221; are actually in the day_tbl   ;o)</p>
]]></content:encoded>
	</item>
	<item>
		<title>By: Justin Swanhart</title>
		<link>http://www.pythian.com/news/1116/good-sql-querying/#comment-233925</link>
		<dc:creator>Justin Swanhart</dc:creator>
		<pubDate>Fri, 11 Jul 2008 00:12:34 +0000</pubDate>
		<guid isPermaLink="false">http://www.pythian.com/blogs/1116/good-sql-querying#comment-233925</guid>
		<description>I find, that if I want to use a reserved word for a table, pluralizing that word often works out well.

days and dates for example</description>
		<content:encoded><![CDATA[<p>I find, that if I want to use a reserved word for a table, pluralizing that word often works out well.</p>
<p>days and dates for example</p>
]]></content:encoded>
	</item>
</channel>
</rss>

