MySQL的开放与使用?
在MySQL JOIN
, ON
和USING()
什么区别? 据我所知, USING()
只是更方便的语法,而ON
允许更多的灵活性,当列名不相同。 然而,这种差异是如此微小,你会认为他们只是废除USING()
。
还有比这个更接近眼睛吗? 如果是,我应该在特定的情况下使用哪一个?
这主要是句法糖,但有一些差异是值得注意的:
ON是两者中较为一般的。 人们可以在一列,一组列甚至一个条件上连接表。 例如:
SELECT * FROM world.City JOIN world.Country ON (City.CountryCode = Country.Code) WHERE ...
当两个表共享一个完全相同的名称的列时, USING非常有用。 在这种情况下,可以说:
SELECT ... FROM film JOIN film_actor USING (film_id) WHERE ...
另外一个很好的方法就是不需要完全限定join列:
SELECT film.title, film_id # film_id is not prefixed FROM film JOIN film_actor USING (film_id) WHERE ...
为了说明,用ON来做上面的事情,我们必须写:
SELECT film.title, film.film_id # film.film_id is required here FROM film JOIN film_actor ON (film.film_id = film_actor.film_id) WHERE ...
注意SELECT
子句中的film.film_id
限定。 只是说film_id
是无效的,因为这会造成模糊:
错误1052(23000):字段列表中的列'film_id'是不明确的
至于select *
,连接列会在结果集中出现两次,并且只有一次显示USING
:
mysql> create table t(i int);insert t select 1;create table t2 select*from t; Query OK, 0 rows affected (0.11 sec) Query OK, 1 row affected (0.00 sec) Records: 1 Duplicates: 0 Warnings: 0 Query OK, 1 row affected (0.19 sec) Records: 1 Duplicates: 0 Warnings: 0 mysql> select*from t join t2 on ti=t2.i; +------+------+ | i | i | +------+------+ | 1 | 1 | +------+------+ 1 row in set (0.00 sec) mysql> select*from t join t2 using(i); +------+ | i | +------+ | 1 | +------+ 1 row in set (0.00 sec) mysql>
当我发现ON
比USING
更有用的时候,我认为我会在这里USING
。 这是当OUTER
连接引入查询。
ON
允许在保持OUTER
连接的同时允许查询被OUTER
连接的表的结果集被限制。 尝试通过指定WHERE
子句来限制结果集,将有效地将OUTER
连接更改为INNER
连接。
当然,这可能是一个相对的angular落案件。 值得推出虽然…..
例如:
CREATE TABLE country ( countryId int(10) unsigned NOT NULL PRIMARY KEY AUTO_INCREMENT, country varchar(50) not null, UNIQUE KEY countryUIdx1 (country) ) ENGINE=InnoDB; insert into country(country) values ("France"); insert into country(country) values ("China"); insert into country(country) values ("USA"); insert into country(country) values ("Italy"); insert into country(country) values ("UK"); insert into country(country) values ("Monaco"); CREATE TABLE city ( cityId int(10) unsigned NOT NULL PRIMARY KEY AUTO_INCREMENT, countryId int(10) unsigned not null, city varchar(50) not null, hasAirport boolean not null default true, UNIQUE KEY cityUIdx1 (countryId,city), CONSTRAINT city_country_fk1 FOREIGN KEY (countryId) REFERENCES country (countryId) ) ENGINE=InnoDB; insert into city (countryId,city,hasAirport) values (1,"Paris",true); insert into city (countryId,city,hasAirport) values (2,"Bejing",true); insert into city (countryId,city,hasAirport) values (3,"New York",true); insert into city (countryId,city,hasAirport) values (4,"Napoli",true); insert into city (countryId,city,hasAirport) values (5,"Manchester",true); insert into city (countryId,city,hasAirport) values (5,"Birmingham",false); insert into city (countryId,city,hasAirport) values (3,"Cincinatti",false); insert into city (countryId,city,hasAirport) values (6,"Monaco",false); -- Gah. Left outer join is now effectively an inner join -- because of the where predicate select * from country left join city using (countryId) where hasAirport ; -- Hooray! I can see Monaco again thanks to -- moving my predicate into the ON select * from country co left join city ci on (co.countryId=ci.countryId and ci.hasAirport) ;
Wikipedia有关于USING
的以下信息:
USING构造不仅仅是语法糖,然而,由于结果集与显式谓词的版本结果集不同。 具体而言,在USING列表中提到的任何列将只出现一次,具有非限定名称,而不是连接中每个表的一次。 在上面的情况下,将会有一个DepartmentID列和没有employee.DepartmentID或department.DepartmentID。
表中讨论的是:
Postgres文档也很好地定义了它们:
ON子句是最常用的一种连接条件:它采用与WHERE子句中使用的相同types的布尔值expression式。 如果ONexpression式的计算结果为true,则T1和T2中的一对行匹配。
USING子句是一种简写,它允许您利用联接的两端对联接列使用相同名称的特定情况。 它使用逗号分隔的共享列名称列表,并形成包含每个列的相等比较的连接条件。 例如,使用USING(a,b)连接T1和T2产生连接条件ON T1.a = T2.a AND T1.b = T2.b.
此外,JOIN USING的输出会抑制冗余列:不需要打印两个匹配的列,因为它们必须具有相同的值。 虽然JOIN ON从T1生成所有列,然后从T2生成所有列,但JOIN USING为每个列出的列对(按列出的顺序)生成一个输出列,其后是来自T1的任何剩余列,随后是来自T2的任何剩余列。