【问题标题】:Sql query - getting history data with time periodSql查询 - 获取具有时间段的历史数据
【发布时间】:2015-03-12 18:20:54
【问题描述】:

我有一些这样的客户的历史记录表,等等:

ID    CLIENT_ID    CITY     STATUS_ID    VALID_FROM    VALID_TO
---------------------------------------------------------------
1     150          NEW YORK 1            2000-01-01    2001-01-01
2     150          NEW YORK 2            2001-01-01    2002-01-01
3     150          NEW YORK 1            2002-01-01    2003-01-01    
4     150          LONDON   1            2003-01-01    2004-01-01
5     150          LONDON   2            2004-01-01    2005-01-01
6     150          NEW YORK 2            2005-01-01    2006-01-01
...

我需要编写一个查询,它将返回这样的数据集

CITY         VALID_FROM    VALID_TO
--------------------------------------
NEW YORK     2000-01-01    2003-01-01
LONDON       2003-01-01    2005-01-01
NEW YORK     2005-01-01    2006-01-01

这意味着我想按年表获取克林特和一座城市的日期。我不在乎状态。 我使用这样的查询:

Select CLIENT_ID, CITY, MIN(VALID_FROM), MAX(VALID_TO)
from HISTORY_TABLE
group by CLIENT_ID, CITY
order by 3 asc

如果 NEW YORK 不再出现在最后显示的行中就好了。

有什么建议吗? 我正在使用 MSSQL 2012

【问题讨论】:

  • 您的查询是正确的。 City 列中可能有脏字符?尝试使用LEN函数就可以了。
  • 问题是该行是唯一的。这可能是因为存在不同的值。
  • 问题是我的查询返回 New York - 2000-01-01 - 2006-01-01 London - 2003-01-01 - 2005-01-01 这与想要的数据不同设置
  • 什么定义了最终结果集中“valid_from”和“valid_to”的正确值?例如,查看您显示的表格,我不确定为什么第一行应该是从 2000 年到 2003 年。是因为连续性,即存在涵盖所有中间时间的其他值吗?我认为您对预期结果集的解释不足以让我帮助处理此类查询。

标签: sql sql-server group-by history


【解决方案1】:
WITH t AS
(
SELECT *, ISNULL(Lag(city,1) OVER(ORDER BY client_id,id), 'first') prevcity, 
ISNULL(Lead(city,1) OVER(ORDER BY client_id,id), 'last') nextcity FROM HISTORY_TABLE
)

SELECT t1.client_id, t1.city, t1.valid_from, ISNULL(t2.valid_to,t1.valid_to) FROM t t1
LEFT JOIN t t2 
ON t1.city=t2.city AND t1.city=t2.prevcity AND t1.client_id=t2.client_id AND t2.city<>t2.nextcity AND t2.id>=t1.id
WHERE t1.city<>t1.prevcity
ORDER BY client_id, id

这个查询试图做的是

  • 将上一个和下一个城市添加到 CTE 表中,以便用于检测主查询中的变化

  • 在主查询中,where 子句确定客户端在新城市开始的行

  • CTE t 保持自我连接,以便为该客户查找下一个城市变化

  • 客户端的最后一条记录将找不到下一个更改,但被 valid_to 的 isnull 覆盖

【讨论】:

  • 谢谢。我对你的代码做了一些修改,但你给了我正确的想法。
猜你喜欢
  • 2012-10-16
  • 1970-01-01
  • 1970-01-01
  • 2022-07-10
  • 2019-01-27
  • 2013-01-27
  • 2021-05-02
  • 1970-01-01
  • 1970-01-01
相关资源
最近更新 更多