0
点赞
收藏
分享

微信扫一扫

sql场景问题记录

河南妞 2024-11-24 阅读 14

1.一条信息多次记录如何查询最后一条数据

在 MySQL 中,如果你想获取每个组中的最后一条新增数据,可以使用一些 SQL 技巧和函数,例如子查询、窗口函数(如果你的 MySQL 版本支持)等。

假设你有一个名为 orders 的表,包含以下列:

  • id: 主键,自增。
  • customer_id: 客户ID。
  • order_date: 订单日期。

你的目标是为每个 customer_id 获取最后一条(即最新)的订单记录。下面是一些方法:

方法一:使用子查询

你可以使用子查询来获取每个组的最大 id 或最大 order_date,然后再进行关联。

SELECT o1.*
FROM orders o1
JOIN (
    SELECT customer_id, MAX(order_date) AS max_order_date
    FROM orders
    GROUP BY customer_id
) o2 ON o1.customer_id = o2.customer_id AND o1.order_date = o2.max_order_date;

方法二:使用窗口函数(适用于 MySQL 8.0 及以上)

MySQL 8.0 及以上版本支持窗口函数,可以更简洁地实现这个需求。

WITH ranked_orders AS (
    SELECT *, 
           ROW_NUMBER() OVER (PARTITION BY customer_id ORDER BY order_date DESC) AS rn
    FROM orders
)
SELECT *
FROM ranked_orders
WHERE rn = 1;

方法三:使用自关联

这是一个较为直观但效率稍低的方法,通过自关联来筛选出每个组的最后一条记录。

SELECT o1.*
FROM orders o1
LEFT JOIN orders o2 ON o1.customer_id = o2.customer_id AND o1.order_date < o2.order_date
WHERE o2.order_date IS NULL;

上述查询的逻辑是,对于每一个 o1 的记录,如果存在一个 o2 记录有相同的 customer_id 但是 order_date 更大,那么 o1 就不是最后一条记录。我们只保留那些找不到更大 order_date 的记录。

选择方法

  • 如果你的 MySQL 版本是 8.0 及以上,推荐使用窗口函数方法,因为它语法简洁且可读性高。
  • 如果你的 MySQL 版本较低,可以使用子查询或自关联的方法。

希望这些方法能帮助你获取每个组中最后一条新增的数据。



2.一条数据中用,分割的方式记录(如 id1,id2,id3)去跟别的表关联查询

表结构如下:

CREATE TABLE su_t_alarm_project (
	alarm_project_id varchar(100) NULL,
	project_name varchar(100) NULL
)
ENGINE=InnoDB
DEFAULT CHARSET=utf8mb4
COLLATE=utf8mb4_general_ci;
-------------------------------------------------
CREATE TABLE su_t_alarm_project_notice (
	alarm_project_ids varchar(100) NULL,
	notice_name varchar(100) NULL
)
ENGINE=InnoDB
DEFAULT CHARSET=utf8mb4
COLLATE=utf8mb4_general_ci;

插入示例数据:

INSERT INTO su_t_alarm_project (alarm_project_id,project_name) VALUES
	 ('test1','测试1') ,('test2','测试2'),('test3','测试3'),('test4','测试4'),('test5','测试5')


INSERT INTO hao_test.su_t_alarm_project_notice (alarm_project_ids,notice_name) VALUES
	 ('test1,test2,test3','test1,test2,test3'), 
	 ('test2,test3,test4','test2,test3,test4'), 
	 ('test2,test5','test2,test5'), 
	 ('test1','test1');

方法一:关联查询  like 方式


select * 
from su_t_alarm_project a 
join su_t_alarm_project_notice n on n.alarm_project_ids like concat('%',a.alarm_project_id,'%')
order by n.alarm_project_ids


方法二:使用子查询(不会写)

在MySQL中将一条记录分割成多条记录的方法。如果你有一个包含分隔符的字段,你可以使用MySQL的SUBSTRING_INDEX()函数来实现。

要分割这个字段,你可以使用以下查询:

SELECT 
  SUBSTRING_INDEX(SUBSTRING_INDEX(t.alarm_project_ids, ',', numbers.n), ',', -1) value,t.notice_name 
FROM
  (SELECT 1 AS n UNION SELECT 2 ) numbers
  INNER JOIN su_t_alarm_project_notice t
  ON CHAR_LENGTH(t.alarm_project_ids)
     -CHAR_LENGTH(REPLACE(t.alarm_project_ids, ',', ''))>=n-1
ORDER BY  numbers.n;	

这个查询使用了一个临时的数字表(这里用子查询表示,实际上可以是一个实际的数字表),然后使用SUBSTRING_INDEX函数两次,分别以逗号为分隔符取第n个值。通过比较字符串长度和替换逗号后的长度,可以确定需要多少次分割。

结果将是:

+--------+| value  |+--------+| value1 || value2 || value3 |+--------+
+--------+| value  |+--------+| value1 || value2 || value3 |+--------+

请根据你的具体需求调整表名、字段名和数据。





举报

相关推荐

0 条评论