带计数的SQL连续记录

时间:2017-01-05 17:52:55

标签: mysql sql

表名称呼叫

Field 1 - Phone_number
Field 2 - System_outcome

Phone_number      System_outcome  DateTime
--------------------------------------------------
07777778999       Answered        18-12-2016 17:15
07777778123       No Answer       18-12-2016 18:10
07777778999       No Answer       19-12-2016 19:30
07777778999       No Answer       19-12-2016 12:15
07777778999       No Answer       19-12-2016 13:15
07777778999       No Answer       20-12-2016 11:15
07777778124       No Answer       20-12-2016 9:15
07777778128       Answered        20-12-2016 17:15
07777778074       Answered        20-12-2016 17:15

以上是一个例子,我需要知道的是如何找到连续无答案数超过6的数字?

目前我已经能够得到以下内容,但它不是连续的。

SELECT phone_number,system_outcome,Datetime
FROM calls
WHERE DATE (datetime) BETWEEN '2016-12-23' AND '2016-12-31'
AND system_outcome = 'NO_ANSWER'
GROUP BY phone_number
HAVING count(Phone_number) > 6

3 个答案:

答案 0 :(得分:2)

您可以使用用户定义的变量来实现此目的。

试试这个:

SELECT DISTINCT
    phone_number
FROM
    (SELECT 
        phone_number,
            System_outcome,
            datetime,
            @rn:=CASE
                WHEN
                    @outcome = system_outcome
                        AND @phone = phone_number
                THEN
                    @rn + 1
                ELSE @rn:=1
            END rn,
            @outcome:=system_outcome,
            @phone:=phone_number
    FROM
        (SELECT 
        phone_number, system_outcome, Datetime
    FROM
        calls
    WHERE DATE (str_to_date(datetime,'%d-%m-%Y %H:%i')) BETWEEN '2016-12-01' AND '2016-12-31'
    ORDER BY phone_number, str_to_date(datetime,'%d-%m-%Y %H:%i')) t1
    CROSS JOIN (SELECT @rn:=0, @outcome:='', @phone:='') t2) t
WHERE
    rn >= 4 AND system_outcome = 'No Answer';

@rn变量将按分区分配(按phone_number分区,system_outcome按datetime排序),然后使用行号和结果类型进行过滤。

答案 1 :(得分:2)

您可以使用变量来执行此操作。

select phone_number from (
select c.*,
@prev_outcome:=@cur_outcome,
@cur_outcome:=system_outcome,
@prev_pnum:=@cur_pnum,
@cur_pnum:=phone_number,
case when @cur_pnum = @prev_pnum and @prev_outcome <> @cur_outcome then @rn:=@rn+1
     when @cur_pnum = @prev_pnum and @prev_outcome = @cur_outcome then @rn:=@rn
else @rn:=1 end as rank
from calls c, 
(select @rn:=0,@prev_pnum:='',@cur_pnum:='',@prev_outcome:='',@cur_outcome:='') r
order by phone_number,dt
    ) x
where system_outcome='No Answer'
group by phone_number,rank
having count(*) > 6

此查询使用4个变量

1)@cur_outcome最初设置为空字符串。此后,select选择当前行的system_outcome。

2)@prev_outcome最初设置为空字符串。此后,select将其设置为@cur_outcome(第一次为空字符串,依此类推)。

3)@cur_pnum,最初设置为空字符串。此后,选择分配当前行的phone_number。

4)@prev_pnum,最初设置为空字符串。此后,select将其设置为@cur_pnum值(最初为空字符串)。

order by子句在此处非常重要,可根据phone_number和date指定当前行和上一行。

最初运行内部查询以查看变量的设置方式,这将为您澄清一些事情。

Sample Demo

该演示包含的一些示例数据比问题中显示的更多。

答案 2 :(得分:0)

这是另一种变体,假设呼叫以它们进入的方式排序

SELECT * FROM (
SELECT  if(System_outcome ='Answered', @con:=0, @con:=@con+1) id, 
    if(Phone_number = @p, @p, @p:=Phone_number) p2,
    CASE
    WHEN Phone_number = @p THEN @con
    ELSE @con:=0 
    END unanswered_count
   ,Phone_number, System_outcome, DateTime
FROM    Table1,
   (SELECT @con:= 0) AS con,
   (SELECT @p:= -1) AS p
) agg
WHERE unanswered_count > 5

已编辑:某些变量名称错误