SQL: Как определить наиболее частую длину данных в столбце БД? - PullRequest
1 голос
/ 01 июля 2019

Необходимо проанализировать длину значений в столбце БД и получить% от числа значений с одинаковой длиной.

Желаемый результат:

            Same length values in COL1 = 70%  with LENGTH = 10 chars

Это не «найти наиболее частое значение и вычислить его длину», потому что, если у нас есть столбец KEY или ID с большим количеством элементов - все значения будут разными.

Нужен быстрый SQL (предпочтителен диалект DB2) - чтобы не перегружать механизм БД (миллиарды строк).

Пример 1

         COL1 (VARCHAR 10) 
         ------------------
                     X01   
                     X02   
                     X03   
                     X04   
                     X05   

Результат:

            100%, 3

Пример 2

           COL1(VARCHAR 20)
         -------------------------
                    New York
                    London
                    Los Angeles
                    Paris
                    San Francisco

Результат:

            20%, 5 
           (or 20%, 13 - does not matter because values are different)

Ответы [ 2 ]

1 голос
/ 02 июля 2019

Один оператор SELECT, использующий оператор GROUP BY GROUPING SETS для любого количества столбцов.В приведенном ниже примере предполагается, что константы являются результатом соответствующей длины (varchar_col).

with tab as (
select
  length(a) a
, length(b) b
, count(1) cnt
, grouping(length(a)) a_grp
, grouping(length(b)) b_grp
from table(values
  ('X01', 'New York')     
, ('X02', 'London')       
, ('X03', 'Los Angeles')  
, ('X04', 'Paris')        
, ('X05', 'San Francisco')
) t (a, b)
group by grouping sets ((length(a)), (length(b)), ())
)
, row_count as (select cnt from tab where a_grp + b_grp = 2)
, top as (
select a, b, cnt, rownumber() over(partition by a_grp, b_grp order by cnt desc) rn_
from tab
where a_grp + b_grp  = 1 -- number of columns - 1
)
select a, b, cnt, 100*cnt/nullif((select cnt from row_count), 0) pst
from top
where rn_=1;

 A  B CNT PST
-- -- --- ---
 3  -   5 100
 -  5   1  20
1 голос
/ 02 июля 2019

Попробуйте:

select concat(cast(rnk1 as float)/cast (totalcol1 as float)*100,'%'), col1length
from (
select *
, row_number () over (partition by col1length order by col1length) rnk1
from (
select length(col1) as col1length
,(select count(col1) from test) as totalcol1
from test)t1
order by rnk1 desc
FETCH FIRST 1 ROWS ONLY)t2

Результат теста:

DB <> Fiddle

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...