代码之家  ›  专栏  ›  技术社区  ›  Hamish Grubijan

请帮助将Tsql“隐式连接”转换为显式连接

  •  4
  • Hamish Grubijan  · 技术社区  · 16 年前

    对不起,我几乎是个不懂SQL的人。这必须在MSFT-SQL、Oracle以及Sybase中工作。在下面的片段中,我需要更改 inner join IJ KL IJ.PO_id = KL.PO_id 变成一个 left join 同时打开 . 所以,我想我得重新考虑一下。嗯,隐式连接不是最可读的,至少在我的同事眼中是这样。我想我会同意的,直到我发展出自己的品味。对不起,为了以防万一,我弄坏了表名和字段名。

    /* @IJ_id is an input stored proc patrameter. */
    from AB, 
         CD,
         EF,
         GH,
         IJ,
         KL
    where
        EF.EF_id = IJ.EF_id and
        IJ.EF_id = AB.EF_id and
        EF.ZY_id = IJ.ZY_id and
        IJ.ZY_id = AB.ZY_id and
        IJ.IJ_id = AB.IJ_id and
        IJ.IJ_id = @IJ_id and
        EF.XW_id = GH.GH_id and
        AB.VU_code = CD.VU_code and
        IJ.TS > 0 and
        IJ.RQ = 0 and
        EF.RQ = 0 and
        AB.RQ = 0 and
        IJ.PO_id = KL.PO_id;
    

    现在,我的困难在于where子句中发生了很多事情。看起来不像 a.b = c.d 将保留在where子句中,但不是所有看起来像 看起来很容易转换为显式联接。最困难的是,理想情况下,条件是在邻居之间- AB+CD , CD+EF , EF+GH GH+IJ , IJ+KL 但他们现在没有那么有组织。我可以重新排序一些,但最终我不想忘记我的目标:我希望新查询不会变慢,而且我希望新查询的可读性不会变差。似乎我最好只修改我需要修改的部分,然后保持原样。我不确定我能不能做到。

    3 回复  |  直到 16 年前
        1
  •  3
  •   Mark Byers    16 年前

    我想应该是这样的:

    FROM AB
    JOIN CD ON AB.VU_code = CD.VU_code
    JOIN IJ ON IJ.EF_id = AB.EF_id AND IJ.ZY_id = AB.ZY_id AND IJ.IJ_id = AB.IJ_id
    JOIN EF ON EF.EF_id = IJ.EF_id AND EF.ZY_id = IJ.ZY_id
    JOIN GH ON EF.XW_id = GH.GH_id
    JOIN KL ON IJ.PO_id = KL.PO_id
    WHERE
        IJ.IJ_id = @IJ_id AND
        IJ.TS > 0 AND
        IJ.RQ = 0 AND
        EF.RQ = 0 AND
        AB.RQ = 0
    

    我试着按照以下规则安排桌子:

    • 每个连接条件都会提到它在一侧连接的新表。
    • 其中一个操作数是常量的条件保留为where条件。

    您需要逐个考虑每个条件:

    • 是对结果的过滤吗?把它放在WHERE子句中。

    • 包含用户参数的条件不太可能是应该移动到联接的条件。
        2
  •  1
  •   Fosco    16 年前

    它的可读性不可能比你给出的例子差。。。

    from AB a
    join CD c on a.VU_Code = c.VU_Code
    join EF e on a.EF_id = e.EF_id and e.RQ = 0
    join GH g on e.XW_id = g.GH_id
    join IJ i on a.IJ_id = i.IJ_id and e.EF_id = i.EF_id
             and a.EF_id = i.EF_id and e.ZY_id = i.ZY_id
             and a.ZY_id = i.ZY_id and i.TS > 0 and i.RQ = 0
    LEFT join KL k on i.PO_id = k.PO_id
    where 
        i.IJ_id = @IJ_id and 
        a.RQ = 0
    
        3
  •  1
  •   OMG Ponies    16 年前

    用途:

     FROM AB t1
     JOIN CD t2 ON t2.VU_code = t1.VU_code
     JOIN GH t4 ON t4.gh_id = t3.xw_id
     JOIN IJ t5 ON t5.ZY_id = t1.ZY_id
               AND t5.IJ_id = t1.IJ_id
               AND t5.EF_id = t1.EF_id 
               AND t5.IJ_id = @IJ_id 
               AND t5.TS > 0 
               AND t5.RQ = 0 
     JOIN EF t3 ON t3.ef_id = t5.ef_id
               AND t3.zy_id = t5.zy_id
               AND t3.RQ = 0
     JOIN KL t6 ON t6.po_id = t5.po_id -- Add LEFT before JOIN for LEFT JOIN
    WHERE ab.qu = 0
    

    它们按照原始ANSI-89语法的顺序使用别名,但是由于别名引用的原因,顺序被调整了-不能在定义表别名之前引用它。