【问题标题】:Mysql: Get count of recordsMysql:获取记录数
【发布时间】:2020-05-05 16:45:22
【问题描述】:

有 2 个 MariaDB(版本 15.1 Distrib 5.5.64-MariaDB,适用于 Linux (x86_64))表:

CREATE TABLE Table1
    (`phone` int, `calldate` datetime)
;

INSERT INTO Table1
    (`phone`, `calldate`)
VALUES
    (123, '2020-01-01 10:00:00'),
    (123, '2020-01-01 11:00:00'),
    (123, '2020-01-01 12:00:00')
;

CREATE TABLE Table2
    (`phone` int, `calldate` datetime)
;

INSERT INTO Table2
    (`phone`, `calldate`)
VALUES
( 123, '2020-01-01 09:01:00'),
( 123, '2020-01-01 09:02:00'),
( 123, '2020-01-01 10:15:00'),
( 123, '2020-01-01 10:20:00'),
( 123, '2020-01-01 10:23:00'),
( 123, '2020-01-01 11:05:00'),
( 123, '2020-01-01 11:12:00'),
( 123, '2020-01-01 11:25:00')
;

如何获得结果: table1 中第一条记录的 calldate (2020-01-01 10:00:00) 比 table2 中两条记录的 calldate 晚。 第二个类似 - 计数为 5(从 09:01:00 到 10:23:00) 但是来自 table2 的两条记录的 calldate 为 09:01:00 和 09:02:00 已经被来自 table1 的第一条记录“重叠”了,所以结果应该是 3 而不是 5。

|------+----------------------+-------+
| phone | calldate            | count |
|-------+---------------------+-------+
| 123   | 2020-01-01 09:02:00 | 2     |
| 123   | 2020-01-01 10:23:00 | 3     |
| 123   | 2020-01-01 11:25:00 | 3     |
|------+---------------------+|------+|

此外,结果集中的调用日期应该是“重叠”子集中的最后一个调用日期。

【问题讨论】:

  • 草莓,我编辑了我的问题
  • 为了提供可靠的答案,我有一些问题想问。首先为什么有2个结构相同的表,有2个相似的表用于插入电话的目的是什么,这2个表之间是否有一定的相关性? table1 是参考表吗?我问这个是因为您在问题中显示的结果集只能由 Table2 中的一个查询提供。
  • Peter Darmis,这些表具有不同的结构,并且没有相互引用。我省略了一些不重要的字段
  • 那么 table1 需要什么?您那里只有三个记录,并且都具有相同的时间结构 XX:00:00。它是一个调度器,它是否表明你想要每小时的结果?

标签: mysql sql mariadb


【解决方案1】:

您可以使用窗口函数来做到这一点:

select t1.phone, t1.calldate, count(t2.phone)
from (select t1.*,
             lead(calldate) over (partition by phone order by calldate) as next_calldate
      from table1 t1
     ) t1 left join
     table2 t2
     on t2.phone = t1.phone and
        t2.calldate >= t1.calldate and
        (t2.calldate < t1.next_calldate or t1.next_calldate is null)
group by t1.phone, t1.calldate;

编辑:

您可以对相关子查询遵循相同的想法:

select t1.phone, t1.calldate, count(t2.phone)
from (select t1.*,
             (select min(tt1.calldate)
              from table1 tt1
              where tt1.calldate > t1.calldate
             ) as next_calldate
      from table1 t1
     ) t1 left join
     table2 t2
     on t2.phone = t1.phone and
        t2.calldate >= t1.calldate and
        (t2.calldate < t1.next_calldate or t1.next_calldate is null)
group by t1.phone, t1.calldate;

这将比窗口函数版本效率更低。

【讨论】:

  • 我的Mysql版本不支持窗口函数。
【解决方案2】:

加入表格并在ON 子句中使用NOT EXISTS,如下所示:

select t1.phone, t1.calldate, count(t2.calldate) count
from Table1 t1 left join Table2 t2
on t2.phone = t1.phone and t2.calldate < t1.calldate
and not exists (
  select 1 from Table1
  where calldate < t1.calldate and t2.calldate < calldate
)  
group by t1.phone, t1.calldate

请参阅demo
结果:

| phone | calldate            | count |
| ----- | ------------------- | ----- |
| 123   | 2020-01-01 10:00:00 | 2     |
| 123   | 2020-01-01 11:00:00 | 3     |
| 123   | 2020-01-01 12:00:00 | 3     |

【讨论】:

    猜你喜欢
    • 2013-02-13
    • 2011-02-17
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2010-12-21
    • 2017-05-23
    • 2019-11-28
    • 1970-01-01
    相关资源
    最近更新 更多