获取所有驾驶执照号码,这些号码等于每个记过码的最大违规数量

inb24sb2  于 2021-07-29  发布在  Java
关注(0)|答案(1)|浏览(385)

我这样做是为了一个统一的任务,任务是基本上得到所有的驾驶执照号码谁有相等的违法行为的最高数额为每个扣分代码。
所以有一个违规表,记过表,和司机表,查询应该返回一个列表,所有的驾驶执照已经获得了每个记过类别最多的罚单,如果有相等的最大值,返回所有的驾驶执照谁得到了该记过类别的最大值。
我使用了一个超级丑陋的嵌套子查询设置,如下所示:

select 
    sp.dem_code as "Demerit Code", 
    dem.dem_description as "Demerit Description", 
    sp2.lic_no as "License No.",
    d.lic_fname || ' ' || d.lic_lname as "Driver Fullname",
    sp."Total Times Booked"
from (
    select
        dem_code,
        max(o.num) as "Total Times Booked"
    from (
        select 
            dem_code, 
            count(lic_no) as num, 
            lic_no 
        from offence 
        group by dem_code, lic_no 
        order by dem_code asc
    ) o
    group by dem_code
    order by dem_code asc
) sp
join (
    select 
        dem_code, 
        count(lic_no) as num, 
        lic_no 
    from offence 
    group by dem_code, lic_no 
    order by dem_code asc
) sp2 on sp."Total Times Booked" = sp2.num and sp.dem_code = sp2.dem_code
join driver d on sp2.lic_no = d.lic_no
join demerit dem on dem.dem_code = sp2.dem_code
order by sp.dem_code asc, sp2.lic_no asc
;

但我不明白为什么会有这样的事情:

select
    dem_code,
    max(num),
    lic_no
from (
select dem_code, count(lic_no) as num, lic_no from offence group by dem_code, lic_no order by dem_code asc
)
group by dem_code
;

select
    dem_code,
    max(num),
    lic_no
from (
select dem_code, count(lic_no) as num, lic_no from offence group by dem_code, lic_no
)
group by dem_code
having num = max(num)
order by dem_code asc
;

不起作用?
它基本上就是要获取所有的许可证号,这些许可证号等于这组错误代码的最大值。

djp7away

djp7away1#

既然可以用sql:d实现,为什么还要用pl/sql呢
假设餐桌冒犯是。。。

(
dem_code varchar2(100),
lic_no varchar2(100),
lic_fname varchar2(100),
... ticket_no varchar2(1),
... ticket_dtls varchar2(1000),
...
);

有两个层次的sql分析窗口函数需要(根据我)。
计算每个扣分代码的每人总数。
计算每个扣分代码的最大侵犯次数或相同扣分代码的所有人的最大(每人扣分总数)。
我们不能在where子句中使用窗口函数,所以需要q1和q2作为两个连续的计算层(input的管道->q1->q2->resultset)。
查询:

With Q1 as (
select 
   dem_code, 
   lic_no, 
   lic_fname,
   -- count per person per demerit code
   count(1) over (partition by dem_code, lic_fname) as fname_dc_num
from offence
),
Q2 as (
select 
   dem_code, 
   lic_no, 
   lic_fname,
   fname_dc_num,
   -- max count by any person for demerit code
   max(fname_dc_num) keep (DENSE_RANK FIRST ORDER BY fname_dc_num desc) over (partition by dem_code) as max_dc_num
from Q1
)
select *
from Q2
where fname_dc_num = max_dc_num
order by dem_code asc, lic_no, lic_fname
;

相关问题