如何扩展SQL语句以包含多个条件?

时间:2019-08-22 17:15:58

标签: sql oracle

我在这里有此SQL语句

SELECT COUNT(*) AS ACB
FROM APPL
WHERE CPTR_APPL_ID LIKE '%(' AND APPL.CRE_TS >= to_date('20190801','yyyymmdd') 
    AND APPL.CRE_TS <  to_date('20190802','yyyymmdd')

现在,这将找到数据库中所有在适当日期以'('符号结尾的应用程序。是否可以扩展此单数查询,以便它与数据库中以A或B或C结尾的其他应用程序一起使用还是什么?它们都需要在同一日期。我只需要计算每种应用程序类型,然后将其放在具有我选择名称的列中即可。

我应该在where部分使用'OR'吗?

2 个答案:

答案 0 :(得分:2)

在我看来,您的代码像Oracle。我认为聚合查询可以满足您的需求:

scm:schema

答案 1 :(得分:2)

多种方式(实际上是多种方式,但是这些方式相对容易理解

选择计数:

WITH cte AS
(
  SELECT CPTR_APPL_ID as typ
  FROM APPL
  WHERE APPL.CRE_TS >= DATE '2019-08-01' AND 
  APPL.CRE_TS < DATE '2019-08-02'
)
SELECT
  (SELECT COUNT(*) FROM cte WHERE typ LIKE '%A') as count_a,
  (SELECT COUNT(*) FROM cte WHERE typ LIKE '%B') as count_b,
  ...
FROM dual

我从不喜欢“选择列表中的选择”查询。根据oracle需要扫描表进行计数的次数,这一性能可能会很差。您希望将cte作为第一步进行处理,这将是减少的结果集,然后将其计算在内,但是您的优化程序可能会以完全不同的方式计划事情

普通的ISO SQL数据透视方法:

  SELECT 
    SUM(CASE WHEN CPTR_APPL_ID LIKE '%A' THEN 1 END) as COUNT_A,
    SUM(CASE WHEN CPTR_APPL_ID LIKE '%B' THEN 1 END) as COUNT_B,
    ...
  FROM APPL
  WHERE APPL.CRE_TS >= DATE '2019-08-01' AND 
  APPL.CRE_TS < DATE '2019-08-02'

我首选的透视方法,因为它适用于所有数据库。基本上是将数据转换为null或1(取决于是否以A结尾(或B等))的情况,然后SUM将所有1求和。总和忽略空值。可以通过不累加的列来扩展,只要这些列在group by中出现即可。性能应该不错,因为它可以一次性处理从WHERE过滤器返回的数据

数据透视语法:

SELECT * FROM
(
  SELECT SUBSTR(CPTR_APPL_ID, -1) as typ
  FROM APPL
  WHERE APPL.CRE_TS >= DATE '2019-08-01' AND 
  APPL.CRE_TS < DATE '2019-08-02'
)
PIVOT 
(
  COUNT(typ)
  FOR typ
  IN ('A', 'B', ...) --this could be a query if you wanted dynamic
)

缺点是它是专有的,但它可以是动态的或固定的列值。有些人真的很认真地学习并记住了语法,而其他人(我)总是必须查找它

让我知道这些查询中是否有错别字-它们是在没有任何测试的情况下编写的。他们都需要对所需的特定代码进行一些调整,希望您可以在所有代码中看到该模式并将其扩展