百分位数

数值数据可以按递增或递减顺序排序。因此,数值数据集的值具有“秩次”(rank order)。百分位数(percentile)是特定秩次上的值。

例如,如果你的考试成绩位于第95百分位数,通常的解释是只有5%的分数高于你。中位数是第50百分位数;通常认为数据集中50%的值位于中位数以上。

但在给出一个适用于所有秩次和所有列表的精确定义时,需要格外小心。为了说明原因,考虑一个极端例子:班上所有学生的考试成绩都是75分。那么75是中位数的自然候选,但50%的分数高于75并不成立。同样,75也是第95百分位数、第25百分位数或任何其他百分位数的自然候选。在定义百分位数时,需要考虑平局(即相等的数据值)。

当相关索引不明确时,你还需要小心确定应该在列表中往上走多远。例如,一个包含10个值的集合的第87百分位数应该是什么?是排序后集合的第8个值、第9个值,还是介于两者之间的某个值?

在本节中,我们将给出一个对所有秩次和所有列表都一致适用的定义。

[In ]:
from datascience import *
%matplotlib inline
path_data = '../../../assets/data/'
import matplotlib.pyplot as plt
plt.style.use('fivethirtyeight')
import numpy as np

数值示例

在给出所有百分位数的通用定义之前,我们将一个值集合的第80百分位数定义为该集合中至少与所有值的80%一样大的最小值。

例如,考虑五个最大洲的面积——非洲、南极洲、亚洲、北美洲和南美洲——四舍五入到最近的百万平方英里。

[In ]:
sizes = make_array(12, 17, 6, 9, 7)

第80百分位数是至少与 sizes 中80%元素一样大的最小值,即五个元素中的五分之四。结果是12:

[In ]:
np.sort(sizes)
array([ 6,  7,  9, 12, 17])

第80百分位数是列表中的一个值,即12。你可以看到80%的值小于或等于它,并且它是列表中满足这一条件的最小值。

类似地,第70百分位数是该集合中至少与 sizes 中70%元素一样大的最小值。5个元素的70%是“3.5个元素”,因此第70百分位数是列表中的第4个元素。对于这些数据,结果也是12,与第80百分位数相同。

percentile 函数

percentile 函数接受两个参数:一个介于0和100之间的秩次,以及一个数组。它返回该数组的对应百分位数。

[In ]:
percentile(70, sizes)
12

通用定义

设 $p$ 为0到100之间的数。一个集合的第 $p$ 百分位数是该集合中至少与所有值的p%一样大的最小值。

根据这个定义,任何值集合的任何介于0和100之间的百分位数都可以计算,并且它始终是该集合中的一个元素。

在实际操作中,假设集合中有 $n$ 个元素。要找到第 $p$ 百分位数: - 将集合按递增顺序排序。 - 计算n的p%:$(p/100) \times n$。称之为 $k$。 - 如果 $k$ 是整数,取排序后集合的第 $k$ 个元素。 - 如果 $k$ 不是整数,将其向上舍入到下一个整数,取排序后集合的该元素。

示例

表格 scores_and_sections 包含一个359人班级中每个学生的行。列是学生的讨论组和期中考试成绩。

[In ]:
scores_and_sections = Table.read_table(path_data + 'scores_by_section.csv')
scores_and_sections
Section | Midterm
1       | 22
2       | 12
2       | 23
2       | 14
1       | 20
3       | 25
4       | 19
1       | 24
5       | 8
6       | 14
... (349 rows omitted)
[In ]:
scores_and_sections.select('Midterm').hist(bins=np.arange(-0.5, 25.6, 1))
Histogram with 'Midterm' on the x-axis and 'Percent per unit' on the y-axis. There is a bar with height of just about 5 is at 0, then there is a gap between that bar and any other comparatively tall bars until about x=10. from x=10 to x=25 bars have varying heights between about 4 to about 7.

成绩的第85百分位数是多少?要使用 percentile 函数,创建一个包含期中考试成绩的数组 scores,然后找出第85百分位数:

[In ]:
scores = scores_and_sections.column(1)
[In ]:
percentile(85, scores)
22

根据百分位数函数,第85百分位数是22。为了检查这与我们的新定义是否一致,让我们直接应用该定义。

首先,将成绩按递增顺序排列:

[In ]:
sorted_scores = np.sort(scores_and_sections.column(1))

数组中有359个成绩。接下来,找出359的85%,即305.15。

[In ]:
0.85 * 359
305.15

这不是整数。根据我们的定义,第85百分位数是 sorted_scores 的第306个元素,按照Python的索引约定,也就是数组的第305项。

[In ]:
# The 306th element of the sorted array

sorted_scores.item(305)
22

这与我们使用 percentile 得到的答案一致。今后,我们将直接使用 percentile

四分位数

数值集合的“第一四分位数”(first quartile)是第25百分位数。这个术语源自“第一个四分之一”。第二四分位数是中位数,第三四分位数是第75百分位数。

对于我们的 scores 数据,这些值分别是:

[In ]:
percentile(25, scores)
11
[In ]:
percentile(50, scores)
16
[In ]:
percentile(75, scores)
20

成绩的分布有时通过第一和第三四分位数之间的“中间50%”区间来概括。