Bạn có thể thử cách này - Tôi sẽ không đảm bảo rằng nó sẽ hoạt động tốt hơn, nhưng đó là cách thông thường của tôi để so sánh một hàng với một hàng "trước đó":
SELECT
* --TODO, list columns
FROM
data d
left join
data d_prev
on
d_prev.time < d.time --TODO - Other key columns?
left join
data d_inter
on
d_inter.time < d.time and
d_prev.time < d_inter.time --TODO - Other key columns?
WHERE
d_inter.time is null AND
(d_prev.value is null OR d_prev.value <> d.value)
(Tôi nghĩ điều này đúng - có thể làm với một số dữ liệu mẫu để xác thực nó).
Về cơ bản, ý tưởng là nối bảng với chính nó và cho mỗi hàng (trong d
), tìm các hàng ứng viên (trong d_prev
) cho hàng "trước đó". Sau đó, thực hiện một phép nối tiếp để cố gắng tìm một hàng (trong d_inter
) tồn tại giữa hàng hiện tại (trong d
) và hàng ứng cử viên (trong d_prev
). Nếu chúng tôi không thể tìm thấy một hàng như vậy (d_inter.time is null
), thì ứng viên đó thực sự là hàng trước đó.