【问题标题】:How to setup WITH queries with two aliases and selects如何使用两个别名和选择设置 WITH 查询
【发布时间】:2016-10-13 03:31:51
【问题描述】:

在 SQL 的开头使用 WITH 构造来执行几个子查询,然后这些子查询可用于 Oracle 中查询的主体(后续)部分的多个位置。

您能否在您的示例中加入或匹配 t2 与 t1,即翻译成我的代码,

WITH t1 as (select * from AA where FIRSTNAME like 'Kermit%'),
     t2 as (select * from BB B join t1 on t1.ID = B.ID)

我想我很清楚 t1 可以在 WITH 的第二段内引用。

括号内的两个选择是不是非常成熟的查询,可以引用不同的表,在需要的条件下使用任何地方?

我不清楚在这种情况下是否可以使用 JOIN 来匹配来自 AA 和 BB 的记录,或者可能是第二个 WITH 子句中的不同连接方法。我见过的一些示例在两个 WITH 子句“下方”的 select 正文中有一个 WHERE A=B。

我在这些 WITH 声明之后遇到的错误是 t2 中的标识符(字段名称)无法识别,但来自 t1 的其余 SQL 引用就好了。似乎 WITH 语法运行正常,但无法访问第二个 WITH 段 (t2) 的结果。

这是整个非工作查询。

with S as (select * from all_records where RESP_MGR like 'Smith%'),
     CHL as (select * from change_log CL JOIN S on S.SERVER_ID = CL.SERVER_ID)

select * from (
   select 
       SERVER_ID as ServerID,
       'Current Environment' as Event,
       SYSDATE as "Date",
       NEW_VALUE as "Data" 
   from CHL
   where OBJECT_DESCR = 'Production'
) 
where "Data" is not null

甲骨文说,

 ORA-00904: "SERVER_ID": invalid identifier
 00904. 00000 -  "%s: invalid identifier"

【问题讨论】:

  • 您描述“分解子查询”(在 WITH 子句中的内容)应该如何工作的方式是正确的。如果您的查询与您编写的虚构示例完全一样,您将不会收到任何错误。您能否显示实际的查询不起作用 - 也许我们可以帮助指出问题所在。 (这不是你对它应该如何工作的理解——这很好。)
  • 你好 mathguy,谢谢。我发布了整个代码和错误消息。错误报告在“当前环境”字样上方有 SERVER_ID 引用的行

标签: sql oracle join common-table-expression


【解决方案1】:

我想这是一个模棱两可的问题。在

CHL as (select * from change_log CL JOIN S on S.SERVER_ID = CL.SERVER_ID)

SELECT * 中有两列称为SERVER_IDS.SERVER_IDCL.SERVER_ID。我猜 Oracle 在它的结果集中给它们起别名 S_SERVER_IDCL_SERVER_ID

解决这个问题的一个简单方法是使用USING 子句

CHL as (select * from change_log CL JOIN S using (SERVER_ID))

【讨论】:

    【解决方案2】:

    Tom Kyte's explanation:

    ANSI SQL 的表引用(相关名称)的范围仅限于一级深度

    换句话说,您的主查询(第一级)将能够引用该列,但由于您的子查询(第二级)超过一个级别,它无法引用该列,这就是原因您收到错误消息。

    我不知道你的表的结构,但我认为你并不真的需要子查询,而是可以使用这样的东西(空气代码):

    with S as (select * from all_records where RESP_MGR like 'Smith%'),
         CHL as (select * from change_log CL JOIN S on S.SERVER_ID = CL.SERVER_ID)
    select 
       SERVER_ID as ServerID,
       'Current Environment' as Event,
       SYSDATE as "Date",
       NEW_VALUE as "Data" 
    from CHL
    where OBJECT_DESCR = 'Production' and NEW_VALUE is not null
    ;
    

    【讨论】:

    • 很好的澄清点,关于我的问题的直接原因。谢谢MJH。我上面的小代码 sn-p 确实包含 SELECT 和其中的子查询,这是实际代码的简化摘录,由于实际需要的查询的复杂性,它需要该结构。所以不幸的是,我可能在使用 WITH 别名的障碍上是“SOL”,并且可能正在寻求其他方法。谢谢你的回答!
    • 没有。 Dave的查询中没有给出级别太深的问题。最外面的查询访问在第二级创建的“数据”。然后第二级查询访问 SERVER_ID,它在第三级中存在两次。级别深度问题发生在另一种情况下,即当您希望将子查询与两个或更多级别的值相关联时。这里没有给出。
    猜你喜欢
    • 1970-01-01
    • 2011-12-21
    • 1970-01-01
    • 1970-01-01
    • 2021-04-30
    • 2017-10-02
    • 1970-01-01
    • 2017-02-16
    • 2017-06-20
    相关资源
    最近更新 更多