6

我有一列数据,其中一些是 NULL 值,我希望从中提取单个 90% 的

ColA
-----
NULL
100
200
300
NULL
400
500
600
700
800
900
1000

对于上述内容,我正在寻找一种技术,它在搜索第 90 个百分位时返回值 900,在第 80 个百分位处返回 800,等等。类似的函数是 AVG(ColA),它为上述数据返回 550,或 MIN( ColA) 返回 100 等。

有什么建议么?

4

3 回答 3

12

如果您想准确获得第 90 个百分位值,不包括 NULL,我建议直接进行计算。以下版本计算行数和行数,并选择合适的值:

select max(case when rownum*1.0/numrows <= 0.9 then colA end) as percentile_90th
from (select colA,
             row_number() over (order by colA) as rownum,
             count(*) over (partition by NULL) as numrows
      from t
      where colA is not null
     ) t

我将条件放在 SELECT 子句而不是 WHERE 子句中,因此您可以轻松获得第 50 个百分位、第 17 个或任何您想要的值。

于 2012-08-10T17:31:05.213 回答
6
WITH
  percentiles AS
(
  SELECT
    NTILE(100) OVER (ORDER BY ColA) AS percentile,
    *
  FROM
    data
)
SELECT
  *
FROM
  percentiles
WHERE
  percentile = 90


注意:如果数据的观测值少于 100 个,则并非所有百分位数都有值。同样,如果您有超过 100 个观察值,则某些百分位数将包含更多值。

于 2012-08-10T17:12:14.027 回答
1

从 SQL Server 2012 开始,有现在PERCENTILE_DISCPERCENTILE_CONT逆分布函数。这些(到目前为止)仅可用作窗口函数,而不是聚合函数,因此由于缺少分组,您必须删除冗余结果,例如使用DISTINCTor TOP 1

WITH t AS (
  SELECT *
  FROM (
    VALUES(NULL),(100),(200),(300),
      (NULL),(400),(500),(600),(700),
      (800),(900),(1000)
  ) t(ColA)
)
SELECT DISTINCT percentile_disc(0.9) WITHIN GROUP (ORDER BY ColA) OVER()
FROM t
;

我在这里更详细地写了关于百分位数的博客

于 2019-01-25T15:25:30.393 回答