使用 group by 和 have 子句计算同一表中子查询的百分比

问题描述

我正在使用 PostGres 10.12 DB,其中包含有关测试的各种字段:

|test_name|result |report_time|main_version|environment|
|    A    |error  |29/11/2020 |     1      |   john    |
|    A    |failure|28/12/2020 |     1      |   john    |
|    A    |error  |29/12/2020 |     1      |   alice   |
|    B    |passed |30/12/2020 |     2      |   ben     |
|    C    |failure|31/12/2020 |     2      |   alice   |
|    A    |error  |31/12/2020 |     2      |   john    |

我正在尝试计算在同一天运行的所有测试中同时具有“失败/错误”和“通过”结果的测试的百分比。

我创建了以下查询

SELECT s.environment,COUNT(*) AS total,COUNT(*)::float / t.total_tests * 100 as percentage
FROM (
     SELECT test_name,environment
     FROM tests where report_time >= Now() - interval '5 day' 
     and main_version='1' and environment='John'
     GROUP BY test_name,environment
     having COUNT(case when result in ('failure','error') then 1 else null end) > 0 
     and count(case when result = 'passed' then 1 else null end) > 0
     order by environment asc
) s
CROSS JOIN (
      SELECT COUNT(*) AS total_tests FROM tests where report_time >= Now() - interval '5 day' 
      and main_version='1' and environment='John'
) t
GROUP BY s.environment,t.total_tests  

这适用于单个环境和版本。当我尝试组合环境时,计数错误
如何正确计算每天的正确百分比?

解决方法

我正在尝试计算在同一天运行的所有测试中同时具有“失败/错误”和“通过”结果的测试的百分比。

我不知道“同一天”指的是什么。示例数据是从五天范围内获取数据,所以我猜这就是您的意思。

无论如何,基本思想是使用条件聚合:

SELECT test_name,environment,AVG( (result = 'passed')::int ) as passed_ratio,AVG( (result in ('failure','error') )::int ) as fail_error_ratio
FROM tests 
WHERE report_time >= now() - interval '5 day'  AND
      main_version = '1' AND
      environment = 'John'
GROUP BY test_name,environment;

这将返回 0 到 1 之间的比率。如果您想要 0 到 100 之间的百分比,只需乘以 100。

相关问答

Selenium Web驱动程序和Java。元素在(x,y)点处不可单击。其...
Python-如何使用点“。” 访问字典成员?
Java 字符串是不可变的。到底是什么意思?
Java中的“ final”关键字如何工作?(我仍然可以修改对象。...
“loop:”在Java代码中。这是什么,为什么要编译?
java.lang.ClassNotFoundException:sun.jdbc.odbc.JdbcOdbc...