【问题标题】:Alternative to UNION ALL in Oracle SQLOracle SQL 中 UNION ALL 的替代方案
【发布时间】:2016-05-18 10:38:26
【问题描述】:

我正在尝试在不使用 UNION ALL 语句的情况下重新创建此查询,我已经尝试过 标量子查询和模型子句,但似乎都没有做我想要的。我的经理不想使用 Union All,但我真的不知道替代方案是什么

任何帮助都会很棒

SELECT null AS UDA_ID,
       'Style-Level Attributes' AS UDA_DESC,
       null AS DISPLAY_TYPE,
       null AS REQUIRED_IND,
       null AS ITEM,
       null AS UDA_TEXT,
       null AS UDA_DATE,
       null AS UDA_VALUE
FROM   DUAL
UNION ALL                 
select a.UDA_ID,
       a.UDA_DESC,
       a.DISPLAY_TYPE,
       a.REQUIRED_IND,
       b.ITEM,
       b.UDA_TEXT,
       b.UDA_DATE,
       b.UDA_VALUE              
from   DAL.P_UDA a,
       FFEDEV.FFE_ITEM_UDA b                
where  a.UDA_ID = b.UDA_ID (+)                
AND    a.REQUIRED_IND IS NOT NULL       
AND    b.ITEM_PARENT IS NULL      
UNION ALL
SELECT null AS UDA_ID,
       'Additional Attributes' AS UDA_DESC,
       null AS DISPLAY_TYPE,
       null AS REQUIRED_IND,
       null AS ITEM,
       null AS UDA_TEXT,
       null AS UDA_DATE,
       null AS UDA_VALUE
FROM   DUAL
UNION ALL                
select a.UDA_ID,
       a.UDA_DESC,
       a.DISPLAY_TYPE,
       a.REQUIRED_IND,
       b.ITEM,
       b.UDA_TEXT,
       b.UDA_DATE,
       b.UDA_VALUE         
from   DAL.P_UDA a,
       FFEDEV.FFE_ITEM_UDA b                
where  a.UDA_ID = b.UDA_ID (+)                
AND    a.REQUIRED_IND IS NULL      
AND    b.ITEM_PARENT IS NULL

【问题讨论】:

  • 这就是创建UNION 的原因。如果您坚持这样做,您可以在所有这些查询之间使用FULL OUTER JOIN ON(1 = 2),并使用NVLCASE EXPRESSION 替换空值,这将与union 相同。
  • 将结果行用作标题很奇怪。选定的行应该只包含数据。因此,您应该在结果行中添加一个包含“样式级别属性”或“附加属性”的列。那么您的查询不能保证按您希望的那样工作。如果没有ORDER BY 子句,则无法保证排序。 UNION ALL 承诺的所有内容是行会出现在结果中,而不是按什么顺序出现。一旦您的查询在并行线程中执行,您可能会看到所有记录都混合在一起。那么你不应该再使用早已被弃用的连接语法。

标签: sql oracle oracle11g union


【解决方案1】:

我注意到,在您的查询中,唯一真正的功能区别在于两个 WHERE 子句。在UNION ALL 的前半部分,条件有:

WHERE a.REQUIRED_IND IS NOT NULL

而下半场有:

WHERE a.REQUIRED_IND IS NULL

您可以使用CASE 表达式来生成包含属性类型的计算列。为清楚起见,这里是 CASE 表达式本身:

CASE WHEN a.REQUIRED_IND IS NOT NULL
    THEN 'Style-Level Attributes'
    ELSE 'Additional Attributes'
END AS UDA_DESC

这是完整的查询:

SELECT CASE WHEN a.REQUIRED_IND IS NOT NULL THEN 'Style-Level Attributes' ELSE 'Additional Attributes' END AS AttrType,
    a.UDA_ID, a.UDA_DESC, a.DISPLAY_TYPE, a.REQUIRED_IND, b.ITEM, b.UDA_TEXT, b.UDA_DATE, b.UDA_VALUE
FROM DAL.P_UDA a
LEFT OUTER JOIN FFEDEV.FFE_ITEM_UDA b
    ON a.UDA_ID = b.UDA_ID
WHERE b.ITEM_PARENT IS NULL
ORDER BY AttrType

此查询中唯一的主要潜在挫折是您丢失了两个空标题行。但是,出于报告目的,应该没有问题。如果你的老板坚持使用那些空标题行,那么告诉他它们是合成数据,将它们添加到结果集中的唯一方法是执行UNION

【讨论】:

  • 我认为您需要删除 REQUIRED_IND IS NOT NULL ,这就是您所解释的。此外,默认的空行将丢失。您还应该使用正确的连接语法在这里回答
  • 这会导致标识符无效,因为第一个语句是从对偶表中选择的,而不是必需的表。
  • 因为我们现在可以包含每条记录的属性类型,所以我已经删除了 null 标题行。相反,我添加了一个具有这种类型的新列。
  • 很好的解释,我同意不应该引入标题行,而是将信息放在一列中。 sagi 是对的,尽管 AND a.REQUIRED_IND IS NOT NULL 会破坏您的意图,并且不鼓励使用过时的连接语法。
  • 我确信必须删除它才能使您的查询按预期工作:-)
猜你喜欢
  • 1970-01-01
  • 1970-01-01
  • 2010-09-17
  • 1970-01-01
  • 2016-09-22
  • 2011-03-13
  • 1970-01-01
  • 2021-09-14
相关资源
最近更新 更多