添加链接
link之家
链接快照平台
  • 输入网页链接,自动生成快照
  • 标签化管理网页链接

1. 表结构

CREATE TABLE `t_iov_help_feedback` (
  `ID` INT(11) NOT NULL  AUTO_INCREMENT COMMENT '主键ID',
  `USER_ID` INT(255) DEFAULT NULL  COMMENT '用户ID',
  `problems` VARCHAR(255) DEFAULT NULL COMMENT '问题描述',
  `last_updated_date` DATETIME DEFAULT NULL COMMENT '最后更新时间',
  PRIMARY KEY (`ID`)
) ENGINE=INNODB DEFAULT CHARSET=utf8;

2. 表数据

INSERT INTO `t_iov_help_feedback`(`ID`, `USER_ID`, `problems`, `last_updated_date`) VALUES (1, 1, '时间比较小', '2021-02-23 10:11:49');
INSERT INTO `t_iov_help_feedback`(`ID`, `USER_ID`, `problems`, `last_updated_date`) VALUES (2, 2, '时间小', '2021-02-23 10:12:49');
INSERT INTO `t_iov_help_feedback`(`ID`, `USER_ID`, `problems`, `last_updated_date`) VALUES (3, 3, '我乱写的', '2021-02-23 11:19:19');
INSERT INTO `t_iov_help_feedback`(`ID`, `USER_ID`, `problems`, `last_updated_date`) VALUES (4, 1, '时间比较大', '2021-02-23 11:16:01');
INSERT INTO `t_iov_help_feedback`(`ID`, `USER_ID`, `problems`, `last_updated_date`) VALUES (5, 2, '时间大', '2021-02-23 11:19:13');

​​在这里插入图片描述
可以看到,USER_ID为1和2都有重复数据。

USER_ID为1 时间最大的条记录为 2021-02-23 11:16:01,USER_ID为2 时间最大的条记录为 2021-02-23 11:19:13。

我们希望找到时间最大的这两条记录。

二、实现方式

1.SQL模板

SELECT
	t1.重复列,
	t1.时间列,
	t1.其余列 
	INNER JOIN ( SELECT t2.重复列, max( t2.时间列 ) AS 时间列 FROM 表 t2 GROUP BY t2.重复列 ) AS t3
	ON t1.重复列 = t3.重复列 AND t1.时间列 = t3.时间列
	GROUP BY t1.重复列

思想:
1)先把该表进行 group by 分组,并查询出每组最大的时间列,得到一个子表。
2)再将原本的表和子表通过重复列和时间列关联起来;
这样查询出来的数据,都是以原表数据为准的,得到了时间最大的记录的所有字段信息。
3)但是如果最近的时间不止一条记录,那么就会出现重复,所以在外层还需要对原表进行group by去重。

2.SQL实现

1)mysql 5.7.5 以下版本sql实现:

-- mysql 5.7.5 以下版本
SELECT
	t1.USER_ID,
	t1.last_updated_date,
	t1.ID,
	t1.problems 
	t_iov_help_feedback t1
	INNER JOIN ( SELECT t2.USER_ID, max( t2.last_updated_date ) AS last_updated_date FROM t_iov_help_feedback t2 GROUP BY t2.USER_ID ) AS t3 
	ON t1.USER_ID = t3.USER_ID AND t1.last_updated_date = t3.last_updated_date
	GROUP BY t1.USER_ID;

2)mysql 5.7.5 及以上版本 sql实现:

-- mysql 5.7.5 及以上版本
SELECT
	t1.USER_ID,
	ANY_VALUE(t1.last_updated_date) as last_updated_date,
	ANY_VALUE(t1.ID) as ID,
	ANY_VALUE(t1.problems) as problems
	t_iov_help_feedback t1
	INNER JOIN ( SELECT t2.USER_ID, max( t2.last_updated_date ) AS last_updated_date FROM t_iov_help_feedback t2 GROUP BY t2.USER_ID ) AS t3 
	ON t1.USER_ID = t3.USER_ID AND t1.last_updated_date = t3.last_updated_date
	GROUP BY t1.USER_ID;

为什么高版本和低版本的sql语句不一样?

这是因为mysql 版本高于5.7.5时,默认设置的 sql_mode 模式是:only_full_group_by。如果没有去除这个默认模式,又使用上述低版本的group by语句,会报以下错误:
在这里插入图片描述
mysql高版本,对报错字段(非group by字段)加了ANY_VALUE()函数可以规避这个问题。
tips:ANY_VALUE()会选择被分到同一组的数据里第一条数据的指定列值作为返回数据。

如果想了解这个错误详情,可以看我的另外篇文章:
MySQL错误-this is incompatible with sql_mode=only_full_group_by完美解决

3.执行结果

1)mysql 5.7.5 以下版本执行结果:
在这里插入图片描述
2)mysql 5.7.5 及以上版本执行结果:
在这里插入图片描述
可以看到,USER_ID为1和2的两条记录,都是取的时间比较近的那条数据。
这样,就达到想要的效果啦~

SELECT fs.*, ROW_NUMBER() OVER(PARTITION BY fs.new_formname ORDER BY fs.new_approvedate DESC) fsp FROM new_flowapproval_steps AS fs ) AS purchase_order_fps WHERE fsp = 1; 如上,其new_formname为可能有多条重复的id栏位,new_ap 这边虽然带出了正确的时间,但是没有带出这条正确时间的result,因此我们需要获到这条时间对应的result。在之前的sql,我只把最近一条时间查出来了,却没有把那条时间对应的结果带出来。 userCode name datetime 107 tom 2017/6/21 22:34 107 tom 2017/6/24 10:21 107   tom 2017/12/7 10:45 107   tom 2017/1/15 14:01 107   tom ... 代码如下: –建立数据表createtable TestData ( ID int identity(1,1) primary key, Data int, ColA varchar(20), ColB varchar(20) ) go –插入测试数据 declare @counts int declare @i int set @counts = 10000 set @i = 1 while @i<=@counts begin insert TestData (Data,ColA,ColB) values(cast(rand()*10000 as int),cast(rand() as va 首先,使用 DISTINCT 关键字去除重复行,这样你就可以得到一个无重复行的结果集。 然后,使用 ORDER BY 子句对结果集进行排序,按照时间字段从最近到最远的顺序排列。 最后,使用 LIMIT 关键字来限制结果集的行数,只保留第一行。 例如,如果你的数据有一个名为 "events" 的表,包含时间字段 "time... select * from om_meeting_schedule s where s.is_use=1 ORDER BY ABS(NOW() - s.meeting_begin_date) ASC limit 1 select * from (select t.*, row_number() over(partition by t.policyno order by t.date desc) rn from tmp_lst_fcbf t) c where rn = 1; 1.时间最新的记录 不分组有重复(多条CreateTime一样的都是最新记录)3.如果Id是uuid类型无法使用max(id)的解决办法(使用开窗函数)2.分组后时间最新的记录。