【问题标题】:Query to get result from checking condition on two-more column from same table查询从同一个表的另外两列的检查条件中获取结果
【发布时间】:2018-06-18 08:03:50
【问题描述】:

我有一张下表:

RuleID |  Code    |    Value
654     Branch          54
654     MessageType     MT103
654     Currency        USD
654     SourceSys       xyz
<!--Comment-Another set of RuleID data-->
656     Branch          54
656     MessageType     MT102
656     Currency        INR
--------So ON -------------
<!--Comment-Another set of RuleID data-->
658     Branch          54
658     MessageType     MT103
658     Currency        INR

每个 RuleID 最多可以有 5 到 6 个代码和它们的值。它可能有 1 也可能有 2。例如,这里我给出了 2 个设置值。一个用于规则 id 654 和其他 656。

现在需要一个查询,我可以在其中获取 Branch = 54 和 MessageType=MT102 的所有 RuleID

我在下面尝试过:-(但这显然行不通)

select RuleID 
from MyTable 
where (CODE='Branch' and Value='54') 
 and  (CODE='MessageType' and Value='MT102') 

也阅读联盟,但这在这里也行不通。

认为加入应该在这里做,但没有得到结果。

预期结果:我想查询 Branch 为 54 且 MessageType 为 MT103 的所有 RuleID。所以预期结果是 Ruleid-654,658

【问题讨论】:

  • 有了样本数据,预期的结果是什么?
  • 用更多数据和预期结果编辑问题

标签: sql oracle oracle11g


【解决方案1】:

使用OR

SELECT RuleID 
FROM MyTable 
WHERE (CODE = 'Branch' AND Value = '54') 
OR (CODE = 'MessageType' AND Value = 'MT102') 

【讨论】:

  • Matt,这就是问题所在,逻辑上我需要 Branch 为 54 且 MessageType 为 MT102 的所有规则 ID。如果 Branch 是 54 并且 MessageType 不是 MT102,那么给定的查询也会导致我。
【解决方案2】:

大概是这样的吧?

SQL> WITH test (ruleid, code, VALUE)
  2       AS (SELECT 654, 'Branch', '54' FROM DUAL
  3           UNION
  4           SELECT 654, 'MessageType', 'MT103' FROM DUAL
  5           UNION
  6           SELECT 654, 'Currency', 'USD' FROM DUAL
  7           UNION
  8           SELECT 654, 'SourceSys', 'xyz' FROM DUAL
  9           UNION
 10           --
 11           SELECT 656, 'Branch', '54' FROM DUAL
 12           UNION
 13           SELECT 656, 'MessageType', 'MT102' FROM DUAL
 14           UNION
 15           SELECT 656, 'Currency', 'INR' FROM DUAL)
 16    SELECT ruleid
 17      FROM test
 18     WHERE (   (    code = 'Branch'
 19                AND VALUE = '54')
 20            OR (    code = 'MessageType'
 21                AND VALUE = 'MT102'))
 22  GROUP BY ruleid
 23    HAVING COUNT (*) = 2;

    RULEID
----------
       656

SQL>

【讨论】:

    【解决方案3】:

    你可以使用交集

    WITH MyTable as 
    (
      SELECT 654 RuleId, 'Branch' code, '54' value FROM DUAL
      UNION
      SELECT 654, 'MessageType', 'MT103' FROM DUAL
      UNION
      SELECT 654, 'Currency', 'USD' FROM DUAL
      UNION
      SELECT 654, 'SourceSys', 'xyz' FROM DUAL
      UNION
      SELECT 656, 'Branch', '54' FROM DUAL
      UNION
      SELECT 656, 'MessageType', 'MT102' FROM DUAL
      UNION
      SELECT 656, 'Currency', 'INR' FROM DUAL
    )
    select RuleID 
    from   MyTable 
    where  CODE='Branch' 
    and    Value='54'
    intersect
    select RuleID 
    from   MyTable 
    where  CODE='MessageType' 
    and    Value='MT102'
    

    【讨论】:

    • 是的 Maxim,这似乎有效,我正在测试多个组合。
    • 我们可以在同一个查询中包含 Null 检查吗?表示如果给定值为 null 则不要与代码相交
    • 好吧,如果我理解正确,那么 null 没有变化,null 会自动从结果集中排除。 Oracle 以特殊方式处理 null - 表达式 code = null 或 code = '' 永远不会为真,结果集为空
    • 不,不是那样,我的意思是在这里,假设 MessageType 是用户输入并且为空,那么我应该获取 Branch 为 54 的所有 RuleID。(MessageType,Branch 是用户输入),他们可能提供价值与否。简而言之,它的过滤器查询
    • 我明白你的意思。如果您能够在应用程序中动态构建查询,那么如果 MessageType 为 null(代表“任何值”) - 您可以简单地省略与 MessageType 查询的交集。但是,如果您无法更改查询并且您唯一更改的是值 - 那么您可以将条件 [value = 'MT102'] 替换为这个 [ (value = 'MT102' or 'MT102'一片空白) ]。因此,如果用户输入为空,则选择每个规则。
    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2023-03-23
    • 1970-01-01
    • 2018-04-28
    • 1970-01-01
    相关资源
    最近更新 更多