根据上次日期选择记录
Posted
技术标签:
【中文标题】根据上次日期选择记录【英文标题】:Select records based on last date 【发布时间】:2013-10-02 09:36:41 【问题描述】:基于下面名为Course
的表:
如何选择课程名称和日期最近的记录?我的意思是,如果我的一个 ID 有两个相同的课程名称,我应该只显示最新的一个作为下面的结果。
简单地说,我只想显示每个(“ID”、“课程名称”)的最新行。
如果我在 Course 表中有两个日期列,即 StartDate 和 EndDate,我想仅根据 EndDate 显示相同的列。
我正在使用 PostgreSQL。
【问题讨论】:
How to select id with max date group by category in PostgreSQL? 的可能重复项 感谢您提出这个问题。很好的例子。 【参考方案1】:在 PostgreSQL 中,为一组定义的列获取唯一行,优选的技术通常是DISTINCT ON
:
SELECT DISTINCT ON ("ID") *
FROM "Course"
ORDER BY "ID", "Course Date" DESC NULLS LAST, "Course Name";
假设您实际上使用了那些带有空格的不幸的大写标识符。
通过这种方式,您恰好得到一行每个ID
- 如果日期出现平局,则具有最新已知"Course Date"
和第一个"Course Name"
(根据排序顺序)的行.
如果您的列定义为NOT NULL
,您可以删除NULLS LAST
。
获取每个 ("ID", "Course Name")
的唯一行:
SELECT DISTINCT ON ("ID", "Course Name") *
FROM "Course"
ORDER BY "ID", "Course Name", "Course Date" DESC NULLS LAST;
此相关答案中的详细信息:
Select first row in each GROUP BY group?【讨论】:
如果我在Course
表中有两个日期列,它们是StartDate
和EndDate
,我想仅基于EndDate
显示相同的列。?
@Aan: ... ORDER BY "ID", "Course Name", "EndDate" DESC NULLS LAST
获取最新"EndDate"
的行。基本上,根据需要按任意数量的列(或表达式)排序。使其明确或从符合条件的同行中任意挑选。我还根据需要将DISTINCT ON
列添加到ORDER BY
,这些在我的初稿中丢失了。
点赞!如果你有一个像 (id, date desc) 这样的 desc 索引,但如果你有 (id, date) 它很慢,我假设这是因为索引在 2 个级别运行,在第一级有 id 然后做一个里面的日期查找,如果索引是 (date, id) 那意味着不需要 date desc 吗?
@PirateApp:(date, id)
上的索引几乎没有用处。你首先需要id
。请点击答案中的链接了解更多信息。另外:dba.stackexchange.com/a/27493/3684 和 dba.stackexchange.com/a/39599/3684
请注意,如果数据库中有 16GB 的记录,这不是一个好的答案。【参考方案2】:
SELECT "ID", "Course Name", MAX("Course Date") FROM "Course" GROUP BY "ID", "Course Name"
【讨论】:
只要没有额外的列就可以了。【参考方案3】:SELECT *
FROM (SELECT ID, CourseName, CourseDate,
MAX(CourseDate) OVER (PARTITION BY COURSENAME) as MaxCourseDate
FROM Course) x
WHERE CourseDate = MaxCourseDate
这里的 MAX() OVER(PARTITION BY) 允许您在派生表中找到每个课程(分区)的最高 CourseDate。然后,您只需选择 CourseDate 等于为该课程找到的最大 Coursedate 的行。
这种方法的好处是不使用 GROUP BY 子句,这将限制您可以返回哪些列,因为 SELECT 子句中的任何非聚合列也必须在 GROUP BY 子句中。
【讨论】:
【参考方案4】:试试这个:
SELECT DISTINCT ON (c."Id", c."Course Name")
c."Id", c."Course Name", c."Course Date"
FROM (SELECT * FROM "Course" ORDER BY "Course Date" DESC) c;
【讨论】:
【参考方案5】:SELECT *
FROM course
GROUP BY id,course name
order by course_date desc
【讨论】:
这是无效的语法。试试吧。 (mysql 可能会接受它,违反标准。)以上是关于根据上次日期选择记录的主要内容,如果未能解决你的问题,请参考以下文章