我想要一个计算字段,它给出了表格中列值的百分位数。这样做的最佳方法是什么?
我有一个只有一列的表,其中包含0到10000之间的值,随机分布。我想添加另一列来告诉我相同行的值相对于原始列中所有其他值的百分位数。
如下所述,有两种百分位定义:http://onlinestatbook.com/chapter1/percentiles.html。
我正在使用我所知道的定义。示例:值为25百分位表示25%的人口为AT或低于该值。
我想到的算法如下,我希望有人可以为我翻译成SQL,因为我是SQL初学者:
对于我表中的所有行,如果该值小于或等于当前行中的值,则计算++。在表的末尾,我做了除法:计数/行数以获得我的百分位数。这对我来说足够准确,因为有很多行。
答案 0 :(得分:5)
[已编辑以匹配相关评论]:
SELECT Number, 100 * (ROW_NUMBER() OVER (ORDER BY Number))/Count(*) AS Percentile
FROM MyTable
如果你的Number
是2,5,10和14,你应该得到:
Number Percentile
2 25
5 50
10 75
14 100
问题在于:如果有重复项,那么ROW_NUMBER会让你失望。如果您的Number
是2,5,5和14,则上面的代码会为您提供:
Number Percentile
2 25
5 50
5 75
14 100
所以......改为做。
SELECT Number, MAX(100 * (ROW_NUMBER() OVER (ORDER BY Number))/Count(*)) AS Percentile
FROM MyTable
GROUP BY Number
如果你的号码是2,5,5,14,它应该返回
Number Percentile
2 25
5 75
14 100
答案 1 :(得分:1)
您不能创建依赖于其他行/表的计算列。
引自MSDN:
表达式可以是非计算的 列名,常量,函数和 这些连接的任何组合 一个或多个运营商。表达方式 不能是子查询。
但是您可以进行查询:
设定:
declare @Test table (Value int)
insert @Test
values
(1),
(2),
(3),
(4),
(5),
(7),
(10)
查询:
select *, (select sum(Value) from @Test t2 where t2.Value <= t1.Value) * 100.0 / sum(Value) over()
from @Test t1
结果:
Value Percentile
----------- ---------------------------------------
1 3.125000000000
2 9.375000000000
3 18.750000000000
4 31.250000000000
5 46.875000000000
7 68.750000000000
10 100.000000000000
答案 2 :(得分:1)
select CAST(SUM(CASE WHEN Number <= 20
THEN 1 ELSE 0 END) as float)/COUNT(*) as PercentileFor20
from Numbers;