mysql 分组取指定条数的数据

本文探讨了在数据量有限的情况下,如何通过复杂的SQL查询来实现分组取样的技术。具体示例展示了从每个分组中选取一条数据的方法,这对于理解和优化数据库查询效率具有重要意义。

在数据条数不足的情况未测试:

表结构如下:

刘德华,周润发,未命名三个分组,每组三条数据

实现三个分组,每组取一条数据

SQL如下:

SELECT
	*
FROM
	(
		(
			SELECT
				g.id,
				g.project_id,
				g.group_name,
				g.group_user_id,
				ug.user_name
			FROM
				t_group g,
				t_user_group ug
			WHERE
				g.id = ug.group_id
		)
	) m
WHERE
	1 > (
		SELECT
			count(*)
		FROM
			(
				SELECT
					g.id,
					g.project_id,
					g.group_name,
					g.group_user_id,
					ug.user_name
				FROM
					t_group g,
					t_user_group ug
				WHERE
					g.id = ug.group_id
			) n
		WHERE
			n.group_user_id = m.group_user_id
		AND n.id < m.id
	)
ORDER BY
	group_user_id

 

MySQL 中实现分组排序后每组第一条数据,通常需要结合排序和分组操作。由于 MySQL 早期版本不支持窗口函数,因此实现方式通常较为复杂。以下介绍几种实现方法: ### 方法一:使用子查询和 `JOIN` 通过子查询获每组排序后的第一条记录的唯一标识(如 `id`),然后使用 `JOIN` 查询获完整的记录。这种方法适用于数据量较小的情况。 ```sql SELECT t1.* FROM your_table t1 INNER JOIN ( SELECT MIN(id) AS min_id -- 假设 id 是唯一标识字段 FROM your_table GROUP BY group_column -- 按照指定分组字段 ) t2 ON t1.id = t2.min_id; ``` 这种方法的核心是通过 `MIN(id)` 获每个分组中第一条记录的唯一标识,然后通过 `JOIN` 获完整的记录信息[^4]。 --- ### 方法二:使用窗口函数(适用于 MySQL 8.0 及以上版本) MySQL 8.0 引入了窗口函数,可以更高效地实现分组排序并每组第一条记录。通过 `ROW_NUMBER()` 函数为每组数据分配一个行号,然后筛选出每组的行号为 1 的记录。 ```sql SELECT * FROM ( SELECT *, ROW_NUMBER() OVER (PARTITION BY group_column ORDER BY sort_column DESC) AS rn FROM your_table ) t WHERE rn = 1; ``` - `PARTITION BY group_column`:按照指定的列对结果集进行分区。 - `ORDER BY sort_column DESC`:在每个分区内按照排序字段进行降序排列。 - `ROW_NUMBER()`:为每行分配一个唯一的行号。 - 最外层查询筛选出行号为 1 的记录,即每组的第一条记录[^5]。 --- ### 方法三:使用 `GROUP BY` 和子查询结合排序 如果数据量较大,但无法使用窗口函数,可以通过排序和 `GROUP BY` 的结合实现分组第一条记录。 ```sql SELECT t.stu_name, t.course_name, t.score FROM ( SELECT * FROM t_student_score ORDER BY score DESC ) t GROUP BY t.course_name; ``` 此方法通过先对数据进行排序,确保每组的第一条记录是排序后的第一条,然后通过 `GROUP BY` 获每组的第一条记录[^2]。 --- ### 方法四:使用临时表和自连接 通过创建临时表存储排序后的数据,然后使用自连接获每组的第一条记录。 ```sql CREATE TEMPORARY TABLE temp_table AS SELECT *, @row_number := IF(@group = group_column, @row_number + 1, 1) AS rn, @group := group_column FROM your_table ORDER BY group_column, sort_column DESC; SELECT * FROM temp_table WHERE rn = 1; ``` - `@row_number` 和 `@group` 是用户变量,用于生成行号。 - 通过 `ORDER BY group_column, sort_column DESC` 确保每组数据按照指定字段排序。 - 最终查询筛选出行号为 1 的记录,即每组的第一条记录。 --- ### 方法比较 1. **方法一**:适用于数据量较小的情况,但效率较低。 2. **方法二**:推荐使用,尤其在 MySQL 8.0 及以上版本中,性能较高且代码简洁。 3. **方法三**:简单易懂,但依赖 `GROUP BY` 的行为,可能在某些版本中表现不一致。 4. **方法四**:灵活且性能较好,适合处理复杂排序需求。 根据实际需求和 MySQL 版本选择合适的方法实现分组排序后每组第一条记录。 ---
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值