我有两列
Key,Val
1 31
2 43
3 41
4 100
我的预期输出是
Key,Val,closestVal
1 31 41
2 43 41
3 41 43
4 100 43
什么是最简单的SQL查询才能获得预期的输出?
答案 0 :(得分:1)
我们可以在此处将ABS
和ROW_NUMBER
一起使用:
WITH cte AS (
SELECT t1.Key, t1.Val, t2.Val AS closestVal,
ROW_NUMBER() OVER (PARTITION BY t1.Key ORDER BY ABS(t1.Val - t2.Val)) rn
FROM yourTable t1
INNER JOIN yourTable t2
ON t1.Key <> t2.Key
)
SELECT Key, Val, closestVal
FROM cte
WHERE rn = 1;
注意:上面的演示适用于SQL Server,不适用于Teradata。如果KEY
是Teradata中的保留关键字,那么如果打算将其用作列名,则必须对其进行转义。
答案 1 :(得分:1)
我认为性能最高的查询将使用lag()
和lead()
-由于某些原因,Teradata不直接支持。但是:
select t.*,
(case when abs(val - min(val) over (order by val rows between 1 preceding and 1 preceding)) <
abs(val - min(val) over (order by val rows between 1 following and 1 following)
then min(val) over (order by val rows between 1 preceding and 1 preceding))
else min(val) over (order by val rows between 1 following and 1 following)
end) as closest_val
from t;
换句话说,不需要子查询或联接,只需要窗口函数即可。