2016-03-06 65 views
0

在WHERE子句中使用UNION和使用OR的左外联接之间是否存在重要的性能考虑因素?使用OR与联盟的左外部联接

这两个查询有什么区别?

使用LEFT OUTER JOIN而不是UNION通常会更好吗?

我问的原因是我实际上需要做INSERT,即使我想要,也不能使用UNION。

SELECT t.foo 
FROM t 
INNER JOIN t1 t1.t_id=t.id 
WHERE t1.id IN (1,2,3) 
UNION 
SELECT t.foo 
FROM t 
INNER JOIN t2 t2.t_id=t.id 
INNER JOIN t2a ON t2a.t2_id=t2.id 
WHERE t2a.id IN (1,2,3) 
UNION 
SELECT t.foo 
FROM t 
INNER JOIN t3 t3.t_id=t.id 
INNER JOIN t3a ON t3a.t3_id=t3.id 
WHERE t3a.id IN (1,2,3); 

SELECT DISTINCT t.foo 
FROM t 
LEFT OUTER JOIN t1 t1.t_id=t.id 
LEFT OUTER JOIN t2 t2.t_id=t.id 
LEFT OUTER JOIN t2a ON t2a.t2_id=t2.id 
LEFT OUTER JOIN t3 t3.t_id=t.id 
LEFT OUTER JOIN t3a ON t3a.t3_id=t3.id 
WHERE t1.id IN (1,2,3) OR t2a.id IN (1,2,3) OR t3a.id IN (1,2,3); 

UPDATE t 
LEFT OUTER JOIN t1 t1.t_id=t.id 
LEFT OUTER JOIN t2 t2.t_id=t.id 
LEFT OUTER JOIN t2a ON t2a.t2_id=t2.id 
LEFT OUTER JOIN t3 t3.t_id=t.id 
LEFT OUTER JOIN t3a ON t3a.t3_id=t3.id 
SET t.foo="bar" 
WHERE t1.id IN (1,2,3) OR t2a.id IN (1,2,3) OR t3a.id IN (1,2,3); 
+1

为什么你不能使用union?检查两个查询的解释计划,运行它们,你将能够看到哪一个更好地执行 – sagi

+0

@sagi你将如何使用UPDATE?无论如何,仍然希望更好地理解这两种方法的含义。 – user1032531

+0

@sagi或者我只是把UNION放在WHERE子句中? – user1032531

回答

2

与许多性能问题一样,您应该在数据和系统上测试结果。 unionleft join正在做非常不同的事情 - 哪个更好可能取决于您的数据的特征,可用的索引和其他考虑因素。

但是,您可以使用union方法在update。你只需要一个子查询:

update t join 
     (select t.id, t1.foo . . . 
     union . . . 
     select t.id, t2.foo 
     ) tt 
     on t.id = tt.id 
    set t.foo = 'foo' 
    where . . .; 

您也可能会发现更有效的使用union方法,但打破了更新成多个独立的update语句。

+0

你是什么意思'你也许会发现使用联合方法更有效率,但将更新分成多个单独的更新语句。 – user1032531

+0

他意味着不是使用union,而是使用第一个选择更新一次,并使用第二个(两个不同的更新语句或更多)更新 – sagi

+0

因此,使用三个单独的查询? – user1032531

2

可以使用UNION插入。

INSERT INTO `table` 
SELECT * FROM 
(
    SELECT '1' 
    UNION 
    SELECT '2' 
) x 

也是一样的更新:

UPDATE `table1` t1 
JOIN (
    SELECT '1' as col1 
    UNION 
    SELECT '2' 
) x ON x.col1 = t1.colX 
SET t1.whateverColumn = "someValue" 

至于性能方面,它的主要下来指标。两者都可以很快,都可以很慢。如果你正确地编制索引,你不应该看到两者之间的巨大差异。