【问题标题】:Need help to simplify this T-SQL query需要帮助来简化此 T-SQL 查询
【发布时间】:2021-07-08 15:45:56
【问题描述】:

我有这个有效的 T-SQL 查询,有什么方法可以简化它吗?

SELECT COUNT(*) FROM Tablename 是重复的,只是每个查询的条件不同,那么有没有办法进一步简化呢?谢谢

SELECT COUNT(*) FROM Table 
WHERE columnA = 'I' AND columnB = 'I' AND columnC =''

UNION ALL

SELECT COUNT(*) FROM Table 
WHERE columnA = 'I' AND columnB = 'I' AND columnC <>''

UNION ALL

SELECT COUNT(*) FROM Table
WHERE columnA IN ('A','R') AND columnB = 'I' AND columnD IN (SELECT columnE FROM Table2)

UNION ALL

SELECT COUNT(*) FROM Table 
WHERE columnA IN ('B') AND columnB = 'I'

UNION ALL

SELECT COUNT(*) FROM Table 
WHERE columnA IN ('R') AND columnB = 'S'

UNION ALL

SELECT COUNT(*) FROM Table 
WHERE columnA IN ('A') AND columnB = 'S'

这是工作查询,我的输出是 6 行,想要保持它

【问题讨论】:

    标签: sql mssql-jdbc


    【解决方案1】:

    让我假设BI_BRH 在STDHOST 中是唯一的。这不是绝对必要的,但它正在简化。

    然后你可以使用条件聚合。我认为将值放在列中是最简单的方法:

    SELECT SUM(CASE WHEN STATUS = 'I' AND TRX_STATE = 'I' AND ASSIGN_TO = '' THEN 1 ELSE 0 END),
           SUM(CASE WHEN STATUS = 'I' AND TRX_STATE = 'I' AND ASSIGN_TO <>'' THEN 1 ELSE 0 END)
           SUM(CASE WHEN STATUS IN ('A','R') AND TRX_STATE = 'I' AND s.BI_BRH IS NOT NULL THEN 1 ELSE 0 END)
           SUM(CASE WHEN STATUS IN ('B') AND TRX_STATE = 'I' THEN 1 ELSE 0 END)
           SUM(CASE WHEN STATUS IN ('R') AND TRX_STATE = 'S' THEN 1 ELSE 0 END)
           SUM(CASE WHEN STATUS IN ('A') AND TRX_STATE = 'S' THEN 1 ELSE 0 END)
    FROM ICSCHQINFO i LEFT JOIN
         STDHOST s
         ON s.BI_BRH = i.BRH_ASSIGN_TO;
    

    【讨论】:

    • 有没有办法以这种格式编写 -> SELECT SUM....... FROM (SELECT........FROM...... WHERE......GROUP BY............UNION ALL SELECT............FROM............WHERE......GROUP BY...... ..)a GROUP BY........
    • @KelveenRaj 。 . .也许。但是,如果您想要单独的行,有更简单的方法可以取消透视。并且不需要显式的GROUP BY。
    【解决方案2】:

    您的代码在同一个表上运行 6 次,在 WHERE 子句中使用不同的条件并返回 6 行。

    假设您拥有的 6 个条件是互斥的,您可以创建一个 CTE,为每一行返回它所属的类别,然后在该类别上聚合:

    WITH cte AS (
      SELECT CASE 
               WHEN STATUS = 'I' AND TRX_STATE = 'I' AND ASSIGN_TO = '' THEN 'cat1'
               WHEN STATUS = 'I' AND TRX_STATE = 'I' AND ASSIGN_TO <> '' THEN 'cat2'
               WHEN STATUS IN ('A','R') AND TRX_STATE = 'I' AND BRH_ASSIGN_TO IN (SELECT BI_BRH FROM STDHOST) THEN 'cat3'
               WHEN STATUS IN ('B') AND TRX_STATE = 'I' THEN 'cat4'
               WHEN STATUS IN ('R') AND TRX_STATE = 'S' THEN 'cat5'
               WHEN STATUS IN ('A') AND TRX_STATE = 'S' THEN 'cat6'
             END category
      FROM ICSCHQINFO          
    )
    SELECT category, COUNT(*) counter
    FROM cte
    GROUP BY category
    

    如果没有任何类别的行,并且在这种情况下您想要一个带有 0 的行,您需要另一个 CTE 来返回类别并将 LEFT 加入到另一个 CTE:

    WITH 
      categories AS (SELECT category FROM (VALUES ('cat1'), ('cat2'), ('cat3'), ('cat4'), ('cat5'), ('cat6')) v(category)),
      cte AS (
        SELECT CASE 
                 WHEN STATUS = 'I' AND TRX_STATE = 'I' AND ASSIGN_TO = '' THEN 'cat1'
                 WHEN STATUS = 'I' AND TRX_STATE = 'I' AND ASSIGN_TO <> '' THEN 'cat2'
                 WHEN STATUS IN ('A','R') AND TRX_STATE = 'I' AND BRH_ASSIGN_TO IN (SELECT BI_BRH FROM STDHOST) THEN 'cat3'
                 WHEN STATUS IN ('B') AND TRX_STATE = 'I' THEN 'cat4'
                 WHEN STATUS IN ('R') AND TRX_STATE = 'S' THEN 'cat5'
                 WHEN STATUS IN ('A') AND TRX_STATE = 'S' THEN 'cat6'
               END category
        FROM ICSCHQINFO          
      )
    SELECT c.category, COUNT(t.category) counter
    FROM categories c LEFT JOIN cte t
    ON t.category = c.category
    GROUP BY c.category
    

    【讨论】:

    • 有没有办法写成这种格式 -> SELECT SUM....... FROM (SELECT........FROM...... WHERE......GROUP BY............UNION ALL SELECT............FROM............WHERE......GROUP BY...... ..)a GROUP BY........
    • @KelveenRaj 为什么?您已经有了 UNION ALL 的代码。你不想简化它吗?
    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2017-08-02
    相关资源
    最近更新 更多