Oracle SQL新手 - 添加获取发生和计算的新列

时间:2018-02-20 04:44:32

标签: sql oracle count

这篇文章是我之前发表的帖子here的增强版。

请注意:这不是重复的帖子或帖子。

我有3张桌子:

1. REQUIRED_AUDITS (Independent table)
2. SCORE_ENTRY (SCORE_ENTRY is One to Many relationship with ERROR table)
3. ERROR 

以下是虚拟数据和表格结构:
REQUIRED_AUDITS TABLE

+-------+------+----------+---------------+-----------------+------------+----------------+---------+
|  ID   |  VP  | Director |    Manager    |    Employee     | Req_audits | Audit_eligible | Quarter |
+-------+------+----------+---------------+-----------------+------------+----------------+---------+
| 10001 | John | King     | susan@com.com | jake@com.com    |          2 | Y              | FY18Q1  |
| 10002 | John | King     | susan@com.com | beth@com.com    |          4 | Y              | FY18Q1  |
| 10003 | John | Maria    | tony@com.com  | david@com.com   |          6 | N              | FY18Q1  |
| 10004 | John | Maria    | adam@com.com  | william@com.com |          3 | Y              | FY18Q1  |
| 10005 | John | Smith    | alex@com.com  | rose@com.com    |          6 | Y              | FY18Q1  |
+-------+------+----------+---------------+-----------------+------------+----------------+---------+

SCORE_ENTRY TABLE

+----------------+------+----------+---------------+-----------------+-------+---------+
| SCORE_ENTRY_ID |  VP  | Director |    Manager    |    Employee     | Score | Quarter |
+----------------+------+----------+---------------+-----------------+-------+---------+
|              1 | John | King     | susan@com.com | jake@com.com    |   100 | FY18Q1  |
|              2 | John | King     | susan@com.com | jake@com.com    |    90 | FY18Q1  |
|              3 | John | King     | susan@com.com | beth@com.com    | 98.45 | FY18Q1  |
|              4 | John | King     | susan@com.com | beth@com.com    |    95 | FY18Q1  |
|              5 | John | King     | susan@com.com | beth@com.com    |   100 | FY18Q1  |
|              6 | John | King     | susan@com.com | beth@com.com    |   100 | FY18Q1  |
|              7 | John | Maria    | adam@com.com  | william@com.com |    99 | FY18Q1  |
|              8 | John | Maria    | adam@com.com  | william@com.com |  98.1 | FY18Q1  |
|              9 | John | Smith    | alex@com.com  | rose@com.com    |    96 | FY18Q1  |
|             10 | John | Smith    | alex@com.com  | rose@com.com    |   100 | FY18Q1  |
+----------------+------+----------+---------------+-----------------+-------+---------+

错误表

+----------+-----------------------------+----------------+
| ERROR_ID |            ERROR            | SCORE_ENTRY_ID |
+----------+-----------------------------+----------------+
|       10 | Words Missing               |              2 |
|       11 | Incorrect document attached |              2 |
|       12 | No results                  |              3 |
|       13 | Value incorrect             |              4 |
|       14 | Words Missing               |              4 |
|       15 | No files attached           |              4 |
|       16 | Document read error         |              7 |
|       17 | Garbage text                |              8 |
|       18 | No results                  |              8 |
|       19 | Value incorrect             |              9 |
|       20 | No files attached           |              9 |
+----------+-----------------------------+----------------+

我的查询提供以下输出:

+----------+---------------+------------------+------------------+------------------+
|          |               | Director Summary |                  |                  |
+----------+---------------+------------------+------------------+------------------+
| Director | Manager       | Audits Required  | Audits Performed | Percent Complete |
| King     | susan@com.com | 6                | 6                | 100%             |
| Maria    | adam@com.com  | 3                | 2                | 67%              |
| Smith    | alex@com.com  | 6                | 2                | 33%              |
+----------+---------------+------------------+------------------+------------------+

现在我想添加列我希望与其相关的错误分数除以分数总数

这不是错误总数除以得分数。而是计算每次出错的次数并除以得分。
请在下面找到例子:

考虑到

导演:特大
经理:susan@com.com

来自 SCORE_ENTRY TABLE和错误表,

  • King在SCORE_ENTRY TABLE中有6个条目
  • ERROR TABLE
  • 中的6个条目

而不是ERROR TABLE中的6个条目,我想发生错误,即3个错误。

计算质量的公式:
质量= 1 - (错误发生总数/总得分)* 100

对于国王: 质量= 1 - (3/6)* 100 质量= 50

请注意:不是1 - (6/6)* 100

玛丽亚: 质量= 1 - (2/2)* 100 质量= 0

以下是我需要的新输出,名为Quality:

+----------+---------------+---------+------------------+------------------+------------------+
|          |               |         | Director Summary |                  |                  |
+----------+---------------+---------+------------------+------------------+------------------+
| Director | Manager       | Quality | Audits Required  | Audits Performed | Percent Complete |
| King     | susan@com.com | 50%     | 6                | 6                | 100%             |
| Maria    | adam@com.com  | 0%      | 3                | 2                | 67%              |
| Smith    | alex@com.com  | 50%     | 6                | 2                | 33%              |
+----------+---------------+---------+------------------+------------------+------------------+

以下是我的查询(感谢@Kaushik Nayak,@ APC等)并且需要在此查询中添加新列:

WITH aud(manager_email, director, quarter, total_audits_required) 
     AS (SELECT manager_email, 
                director, 
                quarter, 
                SUM (CASE 
                       WHEN audit_eligible = 'Y' THEN required_audits 
                     END) 
         FROM   required_audits 
         GROUP  BY manager_email, 
                   director, 
                   quarter), --Total_audits 
     scores(manager_email, director, quarter, audits_completed) 
     AS (SELECT manager_email, 
                director, 
                quarter, 
                Count (score) 
         FROM   oq_score_entry s 
         GROUP  BY manager_email, 
                   director, 
                   quarter) --Audits_Performed 
SELECT a.director, 
       a.manager_email manager, 
       a.total_audits_required, 
       s.audits_completed, 
       Round(( ( s.audits_completed ) / ( a.total_audits_required ) * 100 ), 2) 
                       percentage_complete, 
       a.quarter 
FROM   aud a 
       left outer join scores s 
                    ON a.manager_email = s.manager_email 
WHERE  ( :P4_MANAGER_EMAIL = a.manager_email 
          OR :P4_MANAGER_EMAIL IS NULL ) 
       AND ( :P4_DIRECTOR = a.director 
              OR :P4_DIRECTOR IS NULL ) 
       AND ( :P4_QUARTER = a.quarter 
              OR :P4_QUARTER IS NULL ) 
ORDER  BY a.total_audits_required DESC nulls last 

如果令人困惑或需要更多细节,请告诉我。我愿意接受任何建议和反馈。

感谢任何帮助。

谢谢,
Richa

2 个答案:

答案 0 :(得分:2)

更新:
我的第一个猜测是错误的,我希望现在我做对了。

根据您和shawnt00的评论,您需要计算ERROR表中具有相应条目的分数条目数,并将其用于质量计算。
您可以使用以下表达式计算:

COUNT ((select max(1) from "ERROR" o where o.score_entry_id=s.score_entry_id)) AS error_occurences
当" ERROR"中有条目时,

max(1)返回1否则为NULL。 COUNT跳过空值。
我希望这很清楚。

质量计算为

(1 - error_occurences/audits_completed)*100%

以下是完整脚本,其中manager_email重命名为manager,oq_score_entry重命名为score_entry。 这符合您的计划。我还删除了不必要的WITH列映射,在这种情况下它只会使事情变得复杂。

WITH aud AS (SELECT manager, director, quarter, SUM (CASE 
                   WHEN audit_eligible = 'Y' THEN req_audits 
                 END) total_audits_required 
     FROM   required_audits 
     GROUP  BY manager, director, quarter), --Total_audits 
 scores AS (
 SELECT manager, director, quarter, 
            Count (score) audits_completed,
            COUNT ((select max(1) from "ERROR" o where o.score_entry_id=s.score_entry_id)
                    ) error_occurences -- **  Added **
     FROM   score_entry s 
     GROUP  BY manager, director, quarter
               ) --Audits_Performed 
SELECT a.director, 
   a.manager manager, 
   a.total_audits_required, 
   s.audits_completed, 
   Round(( 1 - ( s.error_occurences ) / ( s.audits_completed )) * 100, 2), -- **  Added **
   Round(( ( s.audits_completed ) / ( a.total_audits_required ) * 100 ), 2) 
                   percentage_complete, 
   a.quarter 
FROM   aud a 
   left outer join scores s ON a.manager = s.manager 
WHERE  ( :P4_manager = a.manager 
      OR :P4_manager IS NULL ) 
   AND ( :P4_DIRECTOR = a.director 
          OR :P4_DIRECTOR IS NULL ) 
   AND ( :P4_QUARTER = a.quarter 
          OR :P4_QUARTER IS NULL ) 
ORDER  BY a.total_audits_required DESC nulls last 

关于total_errors

要添加此列,您可以使用与scores中之前使用的技术类似的技术:

scores AS (
    SELECT manager, director, quarter, 
           count (score) audits_completed,
           count ((select max(1) from "ERROR" o where o.score_entry_id=s.score_entry_id )
                   ) error_occurences,
           sum ( ( SELECT count(*) from "ERROR" o where o.score_entry_id=s.score_entry_id ) 
                   ) total_errors  -- summing error counts for matched score_entry_ids
    FROM   score_entry s 
    GROUP  BY manager, director, quarter
              )

或者您可以重写加入scoresscore_entry的{​​{1}} CTE,这需要在error字段上使用DISTINCT以避免重复行:

score_entry

后一种方法的维护要少一些,因为它需要注意不需要的重复。

另一种(可能是最合适的)方式是制作一个单独的(第三个)CTE,但我不认为该查询足够复杂以保证这一点。

原始答案:
我可能错了,但在我看来,通过"计算每次出错的错误"你试图描述COUNT(DISTINCT expr)。这是计算每个(manager_email,director,quarter)的唯一错误发生。 如果是这样,请稍微更改一下查询:

scores AS (
     SELECT manager, director, quarter, 
            count(DISTINCT s.score_entry_id) audits_completed,
            count(DISTINCT e.score_entry_id ) error_occurences, -- counting distinct score_entry_ids present in Error
            count(e.score_entry_id) total_errors -- counting total rows in Error
     FROM   score_entry s 
                LEFT JOIN "ERROR" e ON s.score_entry_id=e.score_entry_id
     GROUP  BY manager, director, quarter
               )

答案 1 :(得分:1)

一旦有更多数据,主要查询的联接就需要包含导演和季度。

我认为解决这个问题的最简单方法是遵循你已经获得的结构,并添加另一个表格表达式,将其与原始结果相同的方式连接到结果的其余部分。

select manager_email, director, quarter,
    100.0 - 100.0 * count (distinct e.score_entry_id) / count (*) as quality
from score_entry se left outer join error e
    on e.score_entry_id = se.score_entry_id
group by manager_email, director, quarter

如果你的大部分解释都没有必要,那就是简单地说你想要与它们相关的错误分数。很难从你提供的信息中得出结论。