我有这张桌子
ignicao dh_evento
1 2014-09-03 15:08:12
1 2014-09-03 15:08:26
1 2014-09-03 15:08:36
1 2014-09-03 15:08:47
0 2014-09-03 15:09:05
0 2014-09-03 15:39:05
0 2014-09-03 16:09:05
0 2014-09-03 16:39:05
0 2014-09-03 17:09:05
1 2014-09-03 17:09:13
1 2014-09-03 17:09:16
1 2014-09-03 17:09:48
1 2014-09-03 17:09:51
我想得到这个结果:
ignicao dh_evento
1 2014-09-03 15:08:12
0 2014-09-03 15:09:05
1 2014-09-03 17:09:13
我正在执行此查询,但我上面没有得到这个结果。这是我的疑问:
select ignicao, dh_evento from tb_rastreamento
where id_veiculo = 4
and dh_evento between '2014-09-03 00:00:00' and '2014-09-03 23:59:59'
group by ignicao
order by dh_evento
我只得到这个结果:
Ignition dt_event
1 2014-09-03 15:08:12
0 2014-09-03 15:09:05
如何获得超过2行的结果?
我在SQL方面不太好,而且我被困了。
答案 0 :(得分:1)
请记住,SQL通过 value 处理数据,而不是 position 。行不应该有任何隐含的顺序。所以GROUP BY将所有行组合在一起,其值为ignicao = 1,即使它们没有物理存储在表中。
如果您想将第一批1作为一个单独的组处理,则需要引入一个新的枚举来区分它们。您可以向表中添加一列并存储新值,或者在查询中动态执行此操作:
SELECT ignicao, dh_evento, IF(@i=ignicao, @grp, @grp:=@grp+1) AS grp, @i:=ignicao
FROM (SELECT @i:=null, @grp:=0) AS _init, this_table
WHERE dh_evento BETWEEN '2014-09-03 00:00:00' and '2014-09-03 23:59:59'
ORDER BY dh_evento;
只有当ignicao不等于上一行保存的值时,才会增加@grp。
然后,您可以在GROUP BY中使用新列grp
SELECT grp, MAX(ignicao) AS ignicao, MAX(dh_evento) AS dh_evento
FROM (
SELECT ignicao, dh_evento, IF(@i=ignicao, @grp, @grp:=@grp+1) AS grp, @i:=ignicao
FROM (SELECT @i:=null, @grp:=0) AS _init, this_table
WHERE dh_evento BETWEEN '2014-09-03 00:00:00' and '2014-09-03 23:59:59'
ORDER BY dh_evento) AS t
GROUP BY grp;
答案 1 :(得分:1)
使用简单的group by
无法做到这一点。一种方法使用变量:
select r.ignicao, min(dh_evento)
from (select r.ignicao, r.dh_evento,
(@grp := if(@i = @ignicao, @grp,
if(@i := @ignicao, @grp + 1, @grp + 1)
)
) as grp
from tb_rastreamento r cross join
(select @grp := NULL, @i := 0) vars
where id_veiculo = 4 and dh_evento between '2014-09-03 00:00:00' and '2014-09-03 23:59:59'
order by r.ignicao, r.dh_evento
) r
group by grp, r.ignicao;
答案 2 :(得分:0)
select ignicao, min(dh_evento)
from (
select ignicao, dh_evento,
if(@prevIgnicao = ignicao, @groupNum, @groupNum := @groupNum + 1) groupNum,
(@prevIgnicao := ignicao)
from tb_rastreamento
where id_veiculo = 4
and dh_evento between '2014-09-03 00:00:00' and '2014-09-03 23:59:59'
cross join (select @prevIgnicao := null, @groupNum := 0) t1
order by dh_evento
) t1 group by ignicao, groupNum
答案 3 :(得分:0)
或者这个(较慢的)解决方案......为了清晰起见我遗漏了一点......
SELECT a.*
, b.ignicao
FROM
( SELECT x.*
, COUNT(*) rank
FROM my_table x
JOIN my_table y
ON y.dh_evento <= x.dh_evento
GROUP
BY x.dh_evento
) a
LEFT
JOIN
( SELECT x.*
, COUNT(*) rank
FROM my_table x
JOIN my_table y
ON y.dh_evento <= x.dh_evento
GROUP
BY x.dh_evento
) b
ON b.ignicao = a.ignicao
AND b.rank = a.rank - 1
+---------+---------------------+------+---------+
| ignicao | dh_evento | rank | ignicao |
+---------+---------------------+------+---------+
| 1 | 2014-09-03 15:08:12 | 1 | NULL |
| 1 | 2014-09-03 15:08:26 | 2 | 1 |
| 1 | 2014-09-03 15:08:36 | 3 | 1 |
| 1 | 2014-09-03 15:08:47 | 4 | 1 |
| 0 | 2014-09-03 15:09:05 | 5 | NULL |
| 0 | 2014-09-03 15:39:05 | 6 | 0 |
| 0 | 2014-09-03 16:09:05 | 7 | 0 |
| 0 | 2014-09-03 16:39:05 | 8 | 0 |
| 0 | 2014-09-03 17:09:05 | 9 | 0 |
| 1 | 2014-09-03 17:09:13 | 10 | NULL |
| 1 | 2014-09-03 17:09:16 | 11 | 1 |
| 1 | 2014-09-03 17:09:48 | 12 | 1 |
| 1 | 2014-09-03 17:09:51 | 13 | 1 |
+---------+---------------------+------+---------+
答案 4 :(得分:0)
这有效;唯一的问题是没有计算秒数;它们总是显示00.注意我确实为此工作添加了一个唯一的ID列
CREATE TABLE #TEST
(
ID INT,
A INT,
B SMALLDATETIME,
)
INSERT INTO #TEST VALUES(1,1,'2014-09-03 15:08:12')
INSERT INTO #TEST VALUES(2,1,'2014-09-03 15:08:26')
INSERT INTO #TEST VALUES(3,1,'2014-09-03 15:08:36')
INSERT INTO #TEST VALUES(4,1,'2014-09-03 15:08:47')
INSERT INTO #TEST VALUES(5,0,'2014-09-03 15:09:05')
INSERT INTO #TEST VALUES(6,0,'2014-09-03 15:39:05')
INSERT INTO #TEST VALUES(7,0,'2014-09-03 16:09:05')
INSERT INTO #TEST VALUES(8,0,'2014-09-03 16:39:05')
INSERT INTO #TEST VALUES(9,0,'2014-09-03 17:09:05')
INSERT INTO #TEST VALUES(10,1,'2014-09-03 17:09:13')
INSERT INTO #TEST VALUES(11,1,'2014-09-03 17:09:16')
INSERT INTO #TEST VALUES(12,1,'2014-09-03 17:09:48')
INSERT INTO #TEST VALUES(13,1,'2014-09-03 17:09:51')
CREATE TABLE #Test2
(
ID INT,
A INT,
B SMALLDATETIME,
PrevA INT
)
INSERT INTO #Test2
(
ID,
A,
B,
PrevA
)
select
ID,
A,
B,
LAG(A) OVER (ORDER BY ID) AS 'PrevA'
from #TEST
order by B asc
select
A,
B
from #Test2
Where A != PrevA OR PrevA IS NULL