2013-05-11 46 views
4

我需要做一个LEFT JOIN与IF/ELSE,这是我的查询:的if/else LEFT JOIN

IF (M.idArtVar=null, 
    LEFT JOIN ArtMaga G 
      ON (G.idMagazzino = V.idMagazzino AND G.idArticolo = M.idArticolo), 
    LEFT JOIN ArtMaga G 
      ON (G.idMagazzino = V.idMagazzino AND G.idArticolo = M.idArticolo AND 
       G.idArtVar = M.idArtVar) 
    ) 

但它不工作。

我也试过这样:

LEFT JOIN ArtMaga AM 
      ON IF(M.idArtVar IS NULL, 
       (AM.idMagazzino = TM.idMagazzino AND AM.idArticolo = A.idArticoli), 
       (AM.idMagazzino = TM.idMagazzino AND AM.idArtVar = M.idArtVar)) 

但此查询太慢。 我该怎么办? 谢谢。

编辑:这是一个完整的查询:

SELECT F.Codice AS "CodiceFornitore", F.RagioneSociale AS "RagioneSocialeFornitore", A.ArticoloFornitore, C.Descrizione AS CatDes, S.Descrizione AS Settore, U.Sigla AS Um, U2.Sigla AS Um2, A.Moltiplicatore AS Molt, A.Collo, TM. 
dMagazzino, M.idArtVar, AM.Esistenza, AM.Disponibilita,   AM.QtaImpegnata, AM.QtaOrdinata, TM.TipoSoggetto, TM.idSoggetto, ST.DataMovimento, MC.Codice, ST.Quantita, ST.Prezzo, ST.Sconti, M.idMagaRigMov 

    FROM MagaRigMov M 

    LEFT JOIN Articoli  A ON A.idArticoli  = M.idArticolo 
    LEFT JOIN UnMisura  U ON U.idUnMisura  = A.idUnMisura1 
    LEFT JOIN UnMisura  U2 ON U2.idUnMisura = A.idUnMisura2 
    LEFT JOIN Iva   I ON I.idIva   = A.idIva 
    LEFT JOIN Settori  S ON S.idSettori  = A.idSettore 
    LEFT JOIN Fornitori F ON F.idFornitori = A.idFornitore 
    LEFT JOIN ArtCategorie C ON C.idArtCategorie = A.idArtCategoria 
    LEFT JOIN MagaTesMov TM ON TM.idMagaTesMov = M.idMagaTesMov 
    LEFT JOIN STORICO  ST ON (ST.idSoggetto = TM.idSoggetto AND ST.TipoSoggetto = TM.TipoSoggetto AND ST.idArticolo = M.idArticolo) 
    LEFT JOIN MagaCausali MC ON MC.idMagaCausali = ST.idMagaCausale 
    LEFT JOIN ArtMaga  AM ON IF(M.idArtVar IS NULL,(AM.idMagazzino = TM.idMagazzino AND AM.idArticolo = A.idArticoli), 
                 (AM.idMagazzino = TM.idMagazzino AND AM.idArtVar = M.idArtVar)) 

此查询过慢..但工程..

+2

我们可以看到完整的查询和表定义吗? – 2013-05-11 15:40:13

+1

- 特别是索引?另外,你是否意识到两个表达式背后的逻辑是不同的? “太慢”有多慢?与仅使用其中一组连接条件时的性能相比,它有何不同? – 2013-05-11 15:44:47

+1

虽然完整的查询很有趣,但它不如ArtMaga的索引结构有用 - 如果能够使用相关索引,查询将执行得更快。 – 2013-05-11 16:48:04

回答

8

您不能使用IF进行条件连接。因为IF不是SELECT语法的一部分,即使它是(如CASE表达式),也不允许以这种方式使用它。您可以将逻辑移动到ON声明,但:

LEFT JOIN ArtMaga G 
     ON (G.idMagazzino = V.idMagazzino AND G.idArticolo = M.idArticolo) 
      AND M.idArtVar IS NULL 
     OR (G.idMagazzino = V.idMagazzino AND G.idArticolo = M.idArticolo AND 
      G.idArtVar = M.idArtVar) 
      AND M.idArtVar IS NOT NULL 

这可以简化为:

LEFT JOIN ArtMaga G 
     ON (G.idMagazzino = V.idMagazzino AND G.idArticolo = M.idArticolo) 
     AND (M.idArtVar IS NULL OR G.idArtVar = M.idArtVar) 

还要注意,你不能用平等来检查表达式是否为空。
M.idArtVar = null永远不会是真的,因为NULL永远不会等于任何东西(甚至不会等于NULL)。检查表达式是否为空的方法是IS NULL


你的第二个查询,这也就是说,是使用MySQL的IF()功能,似乎是正确的(虽然我看到在代码中的差异与第一查询时,G.idArticolo = M.idArticolo条件已经从一个移除。 )

为什么查询速度慢取决于许多因素,并且在连接条件上使用函数可能是许多因素之一。尝试我上面建议的更改。如果速度仍然很慢,则必须检查执行计划和表上可用的索引。

0

只要把条件on子句。 If不是SQL语句的一部分。

SELECT F.Codice AS "CodiceFornitore", F.RagioneSociale AS "RagioneSocialeFornitore", 
A.ArticoloFornitore, C.Descrizione AS CatDes, S.Descrizione AS Settore, U.Sigla AS Um, U2.Sigla AS Um2, A.Moltiplicatore AS Molt, A.Collo, TM. 
dMagazzino, M.idArtVar, AM.Esistenza, AM.Disponibilita,   AM.QtaImpegnata, AM.QtaOrdinata, TM.TipoSoggetto, TM.idSoggetto, ST.DataMovimento, MC.Codice, ST.Quantita, ST.Prezzo, ST.Sconti, M.idMagaRigMov 

FROM MagaRigMov M 

LEFT JOIN Articoli  A ON A.idArticoli  = M.idArticolo 
LEFT JOIN UnMisura  U ON U.idUnMisura  = A.idUnMisura1 
LEFT JOIN UnMisura  U2 ON U2.idUnMisura = A.idUnMisura2 
LEFT JOIN Iva   I ON I.idIva   = A.idIva 
LEFT JOIN Settori  S ON S.idSettori  = A.idSettore 
LEFT JOIN Fornitori F ON F.idFornitori = A.idFornitore 
LEFT JOIN ArtCategorie C ON C.idArtCategorie = A.idArtCategoria 
LEFT JOIN MagaTesMov TM ON TM.idMagaTesMov = M.idMagaTesMov 
LEFT JOIN STORICO  ST ON (ST.idSoggetto = TM.idSoggetto AND ST.TipoSoggetto = TM.TipoSoggetto AND ST.idArticolo = M.idArticolo) 
LEFT JOIN MagaCausali MC ON MC.idMagaCausali = ST.idMagaCausale 
LEFT JOIN ArtMaga  AM ON (AM.idMagazzino = TM.idMagazzino AND (m.idartVar is NULL and AM.idArtVar = M.idArtVar or AM.idArticolo = A.idArticoli))