SQL Server 2008中的CROSS JOIN和INNER JOIN

CROSS JOININNER JOIN和有什么不一样?

交叉连接:

 SELECT Movies.CustomerID, Movies.Movie, Customers.Age, Customers.Gender, Customers.[Education Level], Customers.[Internet Connection], Customers.[Marital Status], FROM Customers CROSS JOIN Movies 

内部联接:

 SELECT Movies.CustomerID, Movies.Movie, Customers.Age, Customers.Gender, Customers.[Education Level], Customers.[Internet Connection], Customers.[Marital Status] FROM Customers INNER JOIN Movies ON Customers.CustomerID = Movies.CustomerID 

哪一个更好,为什么我会使用其中之一?

交叉连接不合并行,如果每个表中有100行,1对1匹配,则得到10.000个结果,Innerjoin只会在相同的情况下返回100行。

这两个例子将返回相同的结果:

交叉join

 select * from table1 cross join table2 where table1.id = table2.fk_id 

内部联接

 select * from table1 join table2 on table1.id = table2.fk_id 

使用最后的方法

这是Cross Join和Inner Join的最好例子。

考虑下面的表格

表: Teacher

 x------------------------x | TchrId | TeacherName | x----------|-------------x | T1 | Mary | | T2 | Jim | x------------------------x 

表: Student

 x--------------------------------------x | StudId | TchrId | StudentName | x----------|-------------|-------------x | S1 | T1 | Vineeth | | S2 | T1 | Unni | x--------------------------------------x 

1. INNER JOIN

内连接select满足这两个表的行

考虑到我们需要findclass主任老师和相应的学生。 在这种情况下,我们需要应用JOININNER JOIN

在这里输入图像描述

询问

 SELECT T.TchrId,T.TeacherName,S.StudentName FROM #Teacher T INNER JOIN #Student S ON T.TchrId = S.TchrId 
  • SQL FIDDLE

结果

 x--------------------------------------x | TchrId | TeacherName | StudentName | x----------|-------------|-------------x | T1 | Mary | Vineeth | | T1 | Mary | Unni | x--------------------------------------x 

2. CROSS JOIN

交叉连接select第一个表中的所有行和第二个表中的所有行,并显示为笛卡尔积,即具有所有可能性

考虑到我们需要find学校里所有的老师和学生,不pipeclass主任是谁,我们都需要申请CROSS JOIN

在这里输入图像描述

询问

 SELECT T.TchrId,T.TeacherName,S.StudentName FROM #Teacher T CROSS JOIN #Student S 
  • SQL FIDDLE

结果

 x--------------------------------------x | TchrId | TeacherName | StudentName | x----------|-------------|-------------x | T2 | Jim | Vineeth | | T2 | Jim | Unni | | T1 | Mary | Vineeth | | T1 | Mary | Unni | x--------------------------------------x 

CROSS JOIN =(INNER)JOIN =逗号(“,”)

TL; DR CROSS JOIN,SQL(INNER)JOIN和“,”(除了评估顺序优先级较低的逗号之外)的唯一区别是(INNER)JOIN具有ON,而CROSS JOIN和逗号不具有。


重新中间交叉产品

所有这三个产生一个中间的概念SQL风格的笛卡尔交叉产品的所有可能的组合的每行表。 它在ON和/或WHERE减less行数。 SQL小提琴

SQL标准通过跨产品(7.5 1.b.ii),<交叉连接>通过<逗号>(7.7 1.a)和JOIN ON <search条件>通过<逗号>加上WHERE(7.7 1。 b)。

正如维基百科所说:

交叉join

CROSS JOIN从连接中的表中返回行的Cartesian乘积。 换句话说,它将产生将第一个表中的每一行与第二个表中的每一行相结合的行。

内部联接

[…]连接的结果可以定义为首先将表中所有logging的笛卡尔乘积(或交叉连接)(将表A中的每条logging与表B中的每条logging相结合)然后返回所有满足连接谓词的logging。

“隐式连接表示法”只是在SELECT语句的FROM子句中使用逗号分隔它们来列出要连接的表。 因此它指定了一个交叉连接

重新OUTER JOINs&ON VS WHERE看到这个 。

为什么要比较表之间的列?

每个表都包含使某个fill-in-the- [named-] blanks语句成为真的行:

  • 基表包含使某些DBA给定语句为true的行。
 -- rows where movie <Movies.CustomerID> has name <Movies.Movie> and ... SELECT * FROM Movies 
  • 一个连接的中间交叉产品持有的行满足作为其操作数的陈述的声明。
  -- rows where movie <Movies.CustomerID> has name <Movies.Movie> and ... AND customers <Customers.ID> has age <Customers.Age> and ... SELECT * FROM Customers CROSS JOIN Movies 
  • ON和WHERE条件进行AND运算以进一步声明。 该值再次是满足该语句的行。
 -- rows where movie <Movies.CustomerID> has name <Movies.Movie> and ... AND customer <Customers.ID> has age <Customers.Age> and ... AND <Customers.CustomerID> = <Movies.CustomerID> AND <Customers.CustomerAge> >= <Movies.MinimumAge> AND <Customers.Age> = 18 SELECT * FROM Movies JOIN Customers ON Customers.CustomerID = Movies.CustomerID AND Customers.CustomerAge >= Movies.MinimumAge WHERE Customers.Age = 18 

特别是比较表之间相等的列意味着连接表的部分语句对这些列具有相同的值。 只是巧合的是,许多行通常通过表之间的等式比较来移除。

只需为所需行的语句编写SQL即可!

重新查询(和表与条件)的含义看到这一点 。

使用CROSS JOIN vs(INNER)JOIN与逗号

常见的约定是:

  • 当且仅当您不比较表格之间的列时,请使用CROSS JOIN。 这表明缺乏比较是故意的。
  • 使用(INNER)join时,当且仅当您有表之间的比较(加上可能的其他比较)。
  • 不要使用逗号。

通常,也不保存表之间的比较。 但是他们可能不得不放在一个(INNER)JOIN ON中,以获得适当的参数行来进行RIGHT,LEFT或FULL(OUTER)JOIN。

重载“交叉连接”

不幸的是,术语“交叉连接”被用于:

  • 中间交叉产品
  • CROSS JOIN
  • 在没有ON或WHERE的情况下,将一个表中的任何列与另一个列中的任何列进行比较(因为这往往会返回如此多的中间跨产品行)

这些不同的含义变得混乱。 (例如在这里的其他答案和评论。)

PS考虑到CROSS JOIN,(INNER)JOIN和逗号意义上的中间交叉积的作用,上述惯例的论点是不稳定的。 CROSS JOIN或逗号就像(INNER)JOIN在ON状态下一样。 一个中间交叉积,ON和WHERE都在相应的谓词中引入了AND。 然而,INNER JOIN“在一个条件下产生匹配,它只是保持符合条件的 。 ON 必须在SQL中补充逗号的唯一原因是编写OUTER JOIN。 当然,expression的意思应该清楚; 但清晰度是相对于一个特定的理解。)

内部联接

仅显示连接表中具有匹配的行的连接称为内连接。 这是查询和视图devise器中的默认联接。

内部连接的语法

 SELECT t1.column_name,t2.column_name FROM table_name1 t1 INNER JOIN table_name2 t2 ON t1.column_name=t2.column_name 

交叉join

交叉连接产生参与连接的表的笛卡尔乘积。 笛卡尔积的大小是第一个表中的行数乘以第二个表中的行数。

交叉连接的语法

 SELECT * FROM table_name1 CROSS JOIN table_name2 

或者我们也可以用另一种方式来写

 SELECT * FROM table_name1,table_name2 

现在检查下面的查询交叉连接

 SELECT * FROM UserDetails CROSS JOIN OrderDetails 

要么

 SELECT * FROM UserDetails, OrderDetails 

请记住,如果添加了WHERE子句,则交叉联接的行为就像是一个内部联接。 例如,下面的Transact-SQL查询产生相同的结果集。 请参阅http://technet.microsoft.com/en-us/library/ms190690(v=sql.105).aspx

SQL Server也接受简单的表示法:

 SELECT AF, BG, CH FROM TABLE_A A, TABLE_B B, TABLE_C C WHERE AX = BX AND BY = CY 

使用这个简单的符号,不需要担心内连接和交叉连接之间的差异。 有两个“ON”子句,而不是两个“WHERE”子句。 如果您在确定哪些“JOIN”“ON”子句时遇到任何困难,请放弃“JOIN”符号并使用上面较简单的符号。

这不是作弊。

在使用内部联接编写查询的同时,如果两个表满足条件(即两个表中的公共列的精确匹配),则logging将从两个表中提取。

在使用交叉连接写入查询时,结果就像两个表中logging号的笛卡尔乘积。 例如,如果table1包含2条logging,而table2包含3条logging,则查询的结果是2 * 3 = 6条logging。

所以不要去交叉连接,直到你需要。

交叉连接和内部连接是相同的唯一区别在于内部连接我们布尔过滤一些笛卡儿积的结果

 table1 x--------------------------------------x | fieldA | fieldB | fieldC | x----------|-------------|-------------x | A | B | option1 | | A | B1 | option2 | x--------------------------------------x table2 x--------------------------------------x | fieldA | fieldB | fieldC | x----------|-------------|-------------x | A | B | optionB1 | | A1 | B1 | optionB2 | x--------------------------------------x cross join A,B,option1,A,B,optionB1 A,B,option1,A1,B1,optionB2 A,B1,option2,A,B,optionB1 A,B1,option2,A1,B1,optionB2 inner join on field1 (only with the value is the same in both tables) A,B,option1,A,B,optionB1 A,B1,option2,A,B,optionB1 inner join on field1 A,B,option1,A,B,optionB1 

这是我们的数据devise,我们决定只有一个我们正在使用的领域的情况下join。 只join交叉连接两个表,只获得完成特殊布尔expression式的行。

请注意,如果我们正在进行联接的字段在两个表中都是空的,我们将通过filter。 我们或数据库制造商应该添加额外的规则来避免或允许空值。 坚持基础,它只是一个交叉连接,后面跟着一个filter。

内部连接将给出两个表之间匹配logging的结果,因为交叉连接给出了两个表之间可能的组合。