MySQL 获取每个分组最新10条记录的方法

在数据分析中,常常需要对数据库的记录进行分组,并从每个组中提取最新的几条记录。本篇文章将带你了解如何在 MySQL 中实现这一功能。

流程图

首先,我们可以将整个流程概括为以下几个步骤,便于理解:

flowchart TD
    A[获取数据] --> B[分组数据]
    B --> C[为每个分组获取最新记录]
    C --> D[输出结果]

步骤指南

步骤 描述
1 确定要查询的数据表以及分组字段和时间字段
2 使用 ROW_NUMBER() 函数为每个分组的记录分配行号
3 从分配好行号的结果中筛选出最新的10条记录
4 输出最终结果

1. 确定数据表

假设我们有一个名为 orders 的数据表,包含以下字段:idcustomer_idorder_dateamount

2. 使用 ROW_NUMBER() 函数

为了为每个分组的记录分配行号,我们将使用 ROW_NUMBER() 函数。以下是 SQL 代码示例:

SELECT 
    id,
    customer_id,
    order_date,
    amount,
    ROW_NUMBER() OVER (PARTITION BY customer_id ORDER BY order_date DESC) AS row_num
FROM 
    orders;

解释

  • ROW_NUMBER() OVER (PARTITION BY customer_id ORDER BY order_date DESC):按 customer_id 分组,并根据 order_date 降序排列,为每组的记录分配行号。

3. 筛选出最新记录

通过使用之前步骤中的查询结果,我们可以筛选出每个分组的最新 10 条记录:

WITH RankedOrders AS (
    SELECT 
        id,
        customer_id,
        order_date,
        amount,
        ROW_NUMBER() OVER (PARTITION BY customer_id ORDER BY order_date DESC) AS row_num
    FROM 
        orders
)
SELECT 
    id,
    customer_id,
    order_date,
    amount
FROM 
    RankedOrders
WHERE 
    row_num <= 10;

解释

  • WITH RankedOrders AS (...):定义一个 CTE (Common Table Expression) 以临时保存我们前面查询的结果。
  • WHERE row_num <= 10:筛选出每个分组最新的 10 条记录。

关系图

为了更好地理解数据表结构,这里是一个简单的关系图:

erDiagram
    ORDERS {
        int id
        int customer_id
        datetime order_date
        decimal amount
    }
    CUSTOMERS {
        int customer_id
        string name
    }
    ORDERS ||--|| CUSTOMERS : contains

总结

通过以上步骤,我们成功实现了在 MySQL 中获取每个分组最新 10 条记录的功能。使用 ROW_NUMBER() 函数和 CTE 是一种强大的方式来处理类似的需求。掌握这一技巧后,你可以在数据分析或报表生成中更高效地工作。相信通过这些方法的学习,你能更好地运用 SQL 进行数据操作。努力练习,相信你会在开发领域做得越来越出色!