两张桌子......
typedef Node* List
MySQL可以执行"加入"或者"联合"或者可以产生的任何查询:
Table 1:
Name Eyes Hair
---- ---- ----
Able Blue Cyan
Bill Cyan Blue
Sara Blue Blue
Table 2:
Name Hand Foot
---- ---- ----
Carl Left Right
Sara Right Left
答案 0 :(得分:1)
这看起来像是一个“全外部”连接操作。不幸的是,MySQL没有为单个SELECT语句中的此操作提供语法。
幸运的是,可以使用两个SELECT语句模拟完整的外连接。
假设`name`列是主键,或者至少保证是唯一的......
给定名称基本上有三种可能的条件:
(第四个条件,table1或table2中不存在名称值,我们不会关注自己,因为例如Javier没有行源。)
要获得满足第一个条件的行,我们可以使用INNER JOIN
第二个条件,我们可以通过将INNER JOIN转换为LEFT OUTER JOIN来在同一个SELECT中包含这些行。
第三个条件,我们需要一个单独的SELECT,它可以使用反连接模式。 (我们也可以使用NOT EXISTS或NOT IN,但这个特殊的规范是反连接非常适合的。)
我们可以使用UNION ALL设置操作来组合两个SELECT语句的结果。
我们首先获取行,然后处理表达式以获取列
第一个查询
SELECT t1.name
FROM table1 t1
LEFT
JOIN table2 t2
ON t2.name = t1.name
对于第二个查询
SELECT a2.name
FROM table2 a2
LEFT
JOIN table1 a1
ON a1.name = a2.name
WHERE a1.name IS NULL
这里的技巧(反连接模式)是WHERE子句中的条件,它排除了找到匹配项的任何行。所以我们留下来自a2的行,这些行在a1中没有匹配的行。
要使用UNION ALL集合操作来组合这些操作,列的列数和数据类型必须匹配。填写SELECT列表中的表达式,并添加ORDER BY子句,我们得到如下内容:
(未经测试)
(
SELECT t1.name
, t1.eyes
, t1.hair
, t2.hand
, t2.foot
FROM table1 t1
LEFT
JOIN table2 t2
ON t2.name = t1.name
)
UNION ALL
(
SELECT a2.name
, a1.eyes
, a1.hair
, a2.hand
, a2.foot
FROM table2 a2
LEFT
JOIN table1 a1
ON a1.name = a2.name
WHERE a1.name IS NULL
)
ORDER BY `name`
请注意,为了获得那些有序的,我们在每个SELECT周围添加括号,并使用ORDER BY子句跟随最后一个。
同样,在MySQL中,这需要至少两个 SELECT语句。
还有其他查询模式可以返回等效结果,但这些模式需要 more 而不是两个SELECT。
答案 1 :(得分:0)
由于我无法对此进行测试,请注意第一次尝试时这可能不起作用,并且我需要你发布我得到的错误以便我知道(或你可以用一些虚拟数据创建一个SqlFiddle,但你应该能够这样做:
Select Name, Eyes, Hair, Null as Hand, Null as Foot from Table1
Union
Select Name, Null as Eyes, Null as Hair, Hand, Foot from Table2
但是,我认为您最好的办法是重新考虑当前数据库的设置方式。我几乎可以保证你会遇到问题。
答案 2 :(得分:0)
insert table1 (name,eyes,hair) values
('Able','Blue','Cyan'),
('Bill','Cyan','Blue'),
('Sara','Blue','Blue');
insert table2 (name,hand,foot) values
('Carl','Left','Right'),
('Sara','Right','Left');
Select Name, Eyes, Hair, Null as Hand, Null as Foot from table1
where not exists (select * from table2 where table2.name=table1.name)
union
Select Name, Null as Eyes, Null as Hair, Hand, Foot from table2
where not exists (select * from table1 where table1.name=table2.name)
union
select t1.Name,t1.Eyes,t1.Hair,t2.Hand,t2.Foot
from table1 t1
join table2 t2
on t2.Name=t1.Name;
+------+------+------+-------+-------+
| Name | Eyes | Hair | Hand | Foot |
+------+------+------+-------+-------+
| Able | Blue | Cyan | NULL | NULL |
| Bill | Cyan | Blue | NULL | NULL |
| Carl | NULL | NULL | Left | Right |
| Sara | Blue | Blue | Right | Left |
+------+------+------+-------+-------+
4 rows in set (0.00 sec)
我所做的查询有3个部分。第一个是表1中不在表2中。第二个反之亦然。第三部分是共同的(加入)。对于连接,t1和t2表示表名的简单别名。
对于联合的前两部分,我使用not exists
子句而不是NOT IN
子句,因为后者是我从未使用的东西,因为过度偏执危险的NOT IN结果。如果一个人不能很好地了解他们的数据,那么NOT IN可能会返回意外结果,并在数据可空性的情况下浪费大量时间进行调试。
答案 3 :(得分:-1)
SELECT FROM table1
FULL OUTER JOIN table2
ON table1.name = table2.name
WHERE table1.name = null
OR table2.name = null