Това е по-добре да се направи на ниво приложение, но само за забавление, ето го на ниво база данни:
select `user`, `start`, `stop`, diff from (
select
t.*
, if(@prev_user = `user`, (`stop` - @prev) * -1, 0) as diff
, @prev := `start`
, @prev_user := `user`
from
t
, (select @prev := null, @prev_user := null) var_init
order by `user`, `start` desc
) sq
order by `user`, `start`
- вижте как работи на живо в sqlfiddle
Обърнете внимание, че в MySQL няма функции за забавяне/преди. Всичко, което можете да направите, е да използвате променливи. SELECT
клаузата се обработва един ред в даден момент. Така че можете да присвоите стойността на текущия ред в последните редове на SELECT
клауза и следователно използвайте тази променлива като стойност на "предходния ред" в първите редове на SELECT
клауза.
Обърнете внимание също, че ORDER BY
много е важно. Таблица не е сортирана. Данните в релационна СУБД не се сортират, освен ако не посочите поръчка с ORDER BY
клауза.
- прочетете повече за използването на променливи в заявки тук
РЕДАКТИРАНЕ:
Променете го на
UPDATE inactivitytmp
JOIN (
SELECT
inactivitytmp.*
, if(@prev_user_id = `user_id`, (`end_ts` - @prev) * -1, 0) as diff2
, @prev := `start_ts`
, @prev_user_id := `user_id`
FROM
inactivitytmp
, (SELECT @prev := null, @prev_user_id := null) var_init
ORDER BY `user_id`, `start_ts` DESC
) query_alias
ON inactivitytmp.user_id=query_alias.user_id AND inactivitytmp.start_ts=q uery_alias.start_ts AND inactivitytmp.end_ts=query_alias.end_ts
SET inactivitytmp.diff=query_alias.diff2;