【问题标题】:order the nested group based on date in SQLite根据 SQLite 中的日期对嵌套组进行排序
【发布时间】:2015-11-24 07:59:41
【问题描述】:

我的表格如下所示(根据GrandParent、Parent 和Child 分组):

Child | Parent | GrandParent |       Date
---------------------------------------------------
  2   |    1   |    1        | 2015-11-04 01:30:22 
  3   |    1   |    1        | 2015-11-05 01:30:22 
  4   |    4   |    4        | 2015-11-04 01:31:41 
  5   |    5   |    5        | 2015-11-04 01:31:41 
  7   |    7   |    7        | 2014-08-19 03:45:01 
  88  |    8   |    8        | 2014-08-19 03:45:01 
  90  |    8   |    8        | 2014-08-19 03:45:01 
  97  |    8   |    8        | 2015-03-18 03:45:01 
  704 |    8   |    8        | 2015-03-18 03:45:01 
  27  |   11   |    9        | 2015-10-22 06:42:30 
  28  |   11   |    9        | 2015-10-24 06:42:30 
  30  |   12   |    9        | 2015-11-15 06:42:30 
  31  |   12   |    9        | 2015-11-16 06:42:30 

没有Parent 的Child 将自己视为Parent 和GrandParent。

我的目标是对上表进行排序:

  1. GrandParent 最近日期的组应该在顶部
  2. 在GrandParent、Parent 组内,最近日期应位于顶部
  3. 在Parent、Child 内,最近的日期应该在顶部

结果应该是:

Child | Parent | GrandParent |       Date
---------------------------------------------------
  31  |   12   |    9        | 2015-11-16 06:42:30 
  30  |   12   |    9        | 2015-11-15 06:42:30
  28  |   11   |    9        | 2015-10-24 06:42:30 
  27  |   11   |    9        | 2015-10-22 06:42:30  
  3   |    1   |    1        | 2015-11-05 01:30:22 
  2   |    1   |    1        | 2015-11-04 01:30:22
  4   |    4   |    4        | 2015-11-04 01:31:41 
  5   |    5   |    5        | 2015-11-04 01:31:41 
  97  |    8   |    8        | 2015-03-18 03:45:01 
  704 |    8   |    8        | 2015-03-18 03:45:01 
  88  |    8   |    8        | 2014-08-19 03:45:01 
  90  |    8   |    8        | 2014-08-19 03:45:01 
  7   |    7   |    7        | 2014-08-19 03:45:01 

【问题讨论】:

  • 这是什么2015-11-65 ?你确定 7 在 8 之前吗?
  • @GiorgiNakeuri:感谢您的关注,纠正了错误。

标签: sql sqlite android-sqlite


【解决方案1】:

在 ORDER BY 中使用子查询。

select child, parent, grandparent, date
from mytable
order by
  (select max(date) from mytable grp where grp.grandparent = mytable.grandparent) desc,
  (select max(date) from mytable grp where grp.parent = mytable.parent) desc,
  date desc;

【讨论】:

  • 嗯,今天学到了一些新东西。不知道可以在ORDER BY 子句中使用相关子查询。至少在Sql Server 上,它的性能比我的版本好。
  • @Giorgi Nakeuri:这反过来又让 我 感到惊讶。我原以为您的查询要么使用相同的执行计划,要么比我的更好:-)
  • 非常感谢。我相信对上述查询稍作修改将提供如下所示的额外优势 == > select child, parent, grandparent, date from mytable order by (select max(date) from mytable grp where grp.grandparent = mytable.grandparent) desc ,grandparent, (select max(date) from mytable grp where grp.parent = mytable.parent) desc,parent, date desc;
  • @Karthikeyan:不,这不能更快,只会更慢。第一个子查询按grantparents排序,所以先得到9,然后是1、4等。然后你说里面你想按grantparent排序,但是在grantparent 9内,所有记录当然都是grantparent 9。所以这并没有改变任何东西,而只是给 DBMS 额外的工作(如果它没有检测到它的不必要性并简单地跳过它)。
  • @ThorstenKettner:如果两个 GrandParent 或 Parent 具有相同的 max(Date),这可能会导致破坏组(GrandParent、Parent、Child)。尝试在给定链接中使用“mytable” ==> w3schools.com/sql/trysql.asp?filename=trysql_select_all
【解决方案2】:

我想你想要这样的东西:

select t1.* from @t t1
join (select grandparent, max(date) as date from @t group by grandparent) t2 
   on t2.grandparent = t1.grandparent
join (select parent, max(date) as date from @t group by parent) t3 
   on t3.parent = t1.parent
order by t2.date desc, t3.date desc, t1.date desc

您将加入包含 2 个集合的初始表,其中第一个集合代表每个 granparent 的最大日期,第二个代表每个 parents 的最大日期。

小提琴http://sqlfiddle.com/#!7/f304c/4

【讨论】:

  • 非常感谢@Giorgi Nakeuri。
  • @Karthikeyan,这个版本不是和 Thorsten 的 unswer 一样吗?他的版本真的更好。
  • 我相信这在性能方面会更好,因为我在示例中给出的表是通过连接多个表创建的(获取 GrandParent、Parent、Child 关系组)。
  • @Giorgi Nakeuri:非常感谢您提及我的回答。我用我的 DBMS(即 Oracle)做了一些测试,发现我的查询在那里也更快。当然,对于 SQLite,这可能仍然不同。我还尝试了分析函数 MAX OVER(在 SQLite 中不可用),这本来是我最喜欢的,但速度非常慢。显然,有时读取表格两次而不是对其进行排序和重新排序会更快。不过我敢肯定,这只是时间问题,直到 Oracle 的优化器同样有效地处理这一问题。
  • @Karthikeyan:我喜欢 Giorgi 的回答,我不介意你选择了他的回答而不是我的回答。加入聚合数据是一种很好的方法,通常是解决问题的最佳方法。我只想提一下,尽管在编写 SQL 时性能不应该是您首先关心的问题。直接写出您的查询并且易于阅读。只有在遇到性能问题时,您才应该考虑重新编写它。 (当然你可以争辩说你不认为我的查询更具可读性:-) 这只是一个一般性的建议。您的论点“在性能方面更好 [..]”让我写了这个建议。)
猜你喜欢
  • 2012-03-06
  • 2016-05-21
  • 1970-01-01
  • 2022-09-23
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
相关资源
最近更新 更多