您的位置:首页 > 数据库 > MySQL

mysql_如何用mysql计算每组的中位数

2018-01-19 21:19 441 查看
有一天,我不得不计算MySQL中每个组的中位数。 事实证明这并不像听起来那么简单,主要是因为在MySQL中不存在median()函数。 经过一些反复试验和一些有用的提示,我想到了。 尤其对于那些不熟悉MySQL的人来说,这里是我自己写的解决方案。

这是我们的例子。 两组候选人(男性和女性)的一系列数据点。 我们要计算每组的中位高度。




我们先从简单的开始,通过选择两列并按组和高度排序。


SELECT
gender, height
FROM
heights
ORDER BY gender , height ASC


返回以下结果:




接下来,我们需要计算每个组的行数,并将其作为另一列添加到表格中。


SELECT
gender,
height,
(SELECT
COUNT(*)
FROM
heights
WHERE
a.gender = gender) AS total_of_group
FROM
(SELECT
gender, height
FROM
heights
ORDER BY gender , height) AS a


结果:




接下来会变得稍微复杂一些,但这是真正重要的部分。 我们添加了两个变量row_number和median_group。 行数应该每行加1,直到我们到达下一个组,然后再从1开始。我们用median_group帮助变量来实现这个。 在每个结果中,median_group变量设置为行组名(这里是性别)。 案例选择检测是否有组名的变化,并相应地重置计数器。


SET
4000
@ROW_NUMBER:=0;
SET @median_group:='';

SELECT
@ROW_NUMBER:=CASE
WHEN @median_group = gender THEN @ROW_NUMBER + 1
ELSE 1
END AS count_of_group,
@median_group:=gender AS median_group,
gender,
height,
(SELECT
COUNT(*)
FROM
heights
WHERE
a.gender = gender) AS total_of_group
FROM
(SELECT
gender, height
FROM
heights
ORDER BY gender , height) AS a


结果:




现在我们实际计算中位数。

通过将组的计数除以2 (total_of_group / 2.0)并且进行相同的加1操作(total_of_group / 2.0 + 1),我们正在为我们的选择定义一个搜索范围,并将其应用于count_of_group。 这意味着我们只选择在这个范围之间的那些行,有效地选择每个组运行计数的中间值。

我们还将平均值应用于选择(AVG(高度)),因为每个组可能并不总是只有一行被选中。


SET @ROW_NUMBER:=0;
SET @median_group:='';

SELECT
median_group, AVG(height) AS median
FROM
(SELECT
@ROW_NUMBER:=CASE
WHEN @median_group = gender THEN @ROW_NUMBER + 1
ELSE 1
END AS count_of_group,
@median_group:=gender AS median_group,
gender,
height,
(SELECT
COUNT(*)
FROM
heights
WHERE
a.gender = gender) AS total_of_group
FROM
(SELECT
gender, height
FROM
heights
ORDER BY gender , height) AS a) AS b
WHERE
count_of_group BETWEEN total_of_group / 2.0 AND total_of_group / 2.0 + 1
GROUP BY median_group


最后的结果:


内容来自用户分享和网络整理,不保证内容的准确性,如有侵权内容,可联系管理员处理 点击这里给我发消息
标签: