基于周的计数

时间:2013-04-05 14:21:20

标签: sql oracle

我需要以下面的方式检索数据

Weeks  delay_count
0           6         
1           0
2           3
3           4
4           0
5           1           
6           0
7           0    
8           0       
9           0
10          2
11          0        
12          0      
13          0    
14          0
15          3

这里的周是从0到15的硬编码列,delay_count是派生列。我有一个专栏delay_weeks。根据此列中的值,我需要填充delay_count列(派生列)中的值

delay_weeks列值低于。

blank
blank 
blank 
2
10
5
blank 
3
2
10
2
3
3
3
0
0
15
22
29

条件:

  • delay_weeks为空或0时,delay_count列中的计数应为1
  • delay_weeks为3时,delay_count列中的计数应为第3周下的1
  • delay_weeks为10时,delay_count列中的计数应为第10周下的1
  • delay_weeks大于或等于15时,在delay_count列中,第15周的计数应为1。

我写了如下代码

SELECT   "Weeks", a."delay_count"
    FROM (SELECT     LEVEL AS "Weeks"
                FROM DUAL
          CONNECT BY LEVEL <= 15) m,
         (SELECT   VALUE, COUNT (VALUE) AS "delay_numbers"
              FROM (SELECT CASE
                                          WHEN attr11.VALUE >= 15
                                             THEN '15'
                                          ELSE attr11.VALUE
                                       END
                                     VALUE
                      FROM docs,
                           (SELECT object_id, VALUE, attribute_type_id
                              FROM ATTRIBUTES
                             WHERE attribute_type_id =
                                      (SELECT attribute_type_id
                                         FROM attribute_types
                                        WHERE name_display_code =
                                                 'ATTRIBUTE_TYPE.DELAY IN WEEKS')) attr11
                     WHERE docs.obj_id = attr11.object_id(+)

          GROUP BY VALUE) a
   WHERE m."Weeks" = a.VALUE(+)

2 个答案:

答案 0 :(得分:1)

select
  weeks,
  nvl(cnt, 0) as delay_count
from
  (select level-1 as weeks from dual connect by level < 17)
  left join (
    select 
      nvl(least(attr11.value, 15), 0) as weeks,
      count(0) as cnt
    from 
      DOCS 
      left join (
        ATTRIBUTES attr11 
        join ATTRIBUTE_TYPES atr_tp using(attribute_type_id)
      ) 
        on atr_tp.name_display_code = 'ATTRIBUTE_TYPE.DELAY IN WEEKS'
        and docs.obj_id = attr11.object_id
    group by nvl(least(attr11.value, 15), 0)
  ) using(weeks)
order by 1

答案 1 :(得分:1)

对表定义的相关部分进行逆向工程,我认为这可以为您提供所需的内容:

select t.weeks, count(delay) as delay_count
from (select level - 1 as weeks from dual connect by level <= 16) t
left join (
    select case when a.value is null then 0
        when to_number(a.value) > 15 then 15
        else to_number(a.value) end as delay
    from docs d
    left join (
        select a.object_id, a.value
        from attributes a 
        join attribute_types at on at.attribute_type_id = a.attribute_type_id
        where at.name_display_code = 'ATTRIBUTE_TYPE.DELAY IN WEEKS'
    ) a on a.object_id = d.obj_id
) delays on delays.delay = t.weeks
group by t.weeks
order by t.weeks;

我认为匹配的数据是我得到的:

     WEEKS DELAY_COUNT
---------- -----------
         0           6
         1           0
         2           3
         3           4
         4           0
         5           1
         6           0
         7           0
         8           0
         9           0
        10           2
        11           0
        12           0
        13           0
        14           0
        15           3

但很明显,既然你没有给出真正的表格结构,那我就猜测了这些关系。强制性的SQL Fiddle