我有一张表s_log
,显示如下
id | parent_id | log_time | s_value
1 | 1 | 2013-10-09 09:01 | 2.1
2 | 2 | 2013-10-09 09:02 | 9.1 --> hide this
3 | 1 | 2013-10-09 09:04 | 5.2 --> hide this
4 | 2 | 2013-10-09 09:05 | 4.1
5 | 1 | 2013-10-09 09:06 | 2.3
6 | 2 | 2013-10-09 09:07 | 4.2
7 | 1 | 2013-10-09 09:09 | 2.2
8 | 2 | 2013-10-09 09:10 | 4.9
9 | 2 | 2013-10-09 09:11 | 5.7
10 | 2 | 2013-10-09 09:12 | 6.3
11 | 2 | 2013-10-09 09:13 | 2.3 --> hide this
12 | 2 | 2013-10-09 09:14 | 5.8
13 | 2 | 2013-10-09 09:15 | 6.5
14 | 2 | 2013-10-09 09:16 | 9.5 --> hide this
要求是:
例如,当parent_id = 1
时 2.1 - 5.2 - 2.3 - 2.2
\ 3.1 \ 2.9 \ 0.1
BAD BAD OK
所以5.2必须隐藏
parent_id = 2时的另一个例子
9.1 - 4.1 - 4.2 - 4.9 - 5.7 - 6.3 - 2.3 - 5.8 - 6.5 - 9.6
\ 5.0 \ 0.1 \ 0.7 \ 0.8 \ 0.6 \ 4.0 \ 2.5 \ 0.7 \ 3.0
BAD OK OK OK OK BAD BAD OK BAD
我的老板问的很不可能......
编辑:尽可能使用PostgreSQL 9.3
答案 0 :(得分:1)
使用递归查询,我们可以将每一行与之前的行进行比较,即使它没有先前的ID(少一个)。
尝试这样的事情:
DECLARE @tbl TABLE
(
[ID] INT,
[PARENT_ID] INT,
[LOG_TIME] DATETIME,
[S_VALUE] NUMERIC(4, 2),
RN INT
)
INSERT @tbl
SELECT *,
ROW_NUMBER()
OVER (
PARTITION BY PARENT_ID
ORDER BY ID) RN
FROM TABLE1
;WITH CTE
AS (SELECT *,
CAST(0 AS NUMERIC(4, 2)) AS diff
FROM @tbl
WHERE RN = 1
UNION ALL
SELECT T2.*,
ABS(CAST(T1.S_VALUE - T2.S_VALUE AS NUMERIC(4, 2))) diff
FROM CTE T1
INNER JOIN @tbl T2
ON T1.RN = T2.RN - 1
AND T1.PARENT_ID = T2.PARENT_ID)
SELECT ID,
PARENT_ID,
LOG_TIME,
S_VALUE
FROM CTE
WHERE DIFF < 1
可以在SQL Fiddle找到一个工作示例。
如果您使用的是SQL 2012,则可以使用更简单的解决方案
使用LAG
或LEAD
函数可以在更短更简单的代码中获得相同的结果。