如何在SQL Server中对日期范围进行透视生成不重叠起止日期?
没问题,我来帮你实现这个日期透视的需求——按sID分组,让每个Key对应的时间段连续不重叠,最新记录的结束日期固定为2050-12-30,前序记录的结束日期刚好是下一条记录开始日期的前一天。下面给你两种常用的实现方案:
SQL 实现方案(适用于支持窗口函数的数据库)
如果你的数据存在数据库中(比如PostgreSQL、MySQL 8.0+、SQL Server等),可以用窗口函数快速实现:
WITH ranked_records AS ( SELECT sID, Key, date AS start_date, -- 按sID分组,日期倒序排号,最新的记录排第1 ROW_NUMBER() OVER (PARTITION BY sID ORDER BY date DESC) AS record_rank, -- 获取同组下一条记录的开始日期 LEAD(date) OVER (PARTITION BY sID ORDER BY date DESC) AS next_start FROM your_dataset_table ) SELECT sID, Key, start_date, CASE -- 组内第一条(最新)记录用指定结束日期 WHEN record_rank = 1 THEN '2050-12-30'::DATE -- 其他记录的结束日期是下一条记录开始日期的前一天 ELSE next_start - INTERVAL '1 day' END AS end_date FROM ranked_records -- 按sID和开始日期倒序排列,和示例输出一致 ORDER BY sID, start_date DESC;
执行这个查询后,就能得到你想要的结果:
sID Key start_date end_date
AAA 123 2009-05-27 2050-12-30
AAA 457 1985-01-01 2009-05-26
BBB 785 2008-09-05 2050-12-30
BBB 890 1900-01-01 2008-09-04
Python Pandas 实现方案
如果用Python处理本地数据,Pandas是很方便的工具:
import pandas as pd # 1. 构造示例数据(如果是读取本地文件,替换成pd.read_csv等方法) data = { 'sID': ['AAA', 'AAA', 'BBB', 'BBB'], 'Key': [123, 457, 890, 785], 'date': ['2009-05-27', '1985-01-01', '1900-01-01', '2008-09-05'] } df = pd.DataFrame(data) df['date'] = pd.to_datetime(df['date']) # 转成日期格式 # 2. 按sID分组,组内按日期倒序排序 sorted_df = df.groupby('sID', group_keys=False).apply(lambda x: x.sort_values('date', ascending=False)).reset_index(drop=True) # 3. 获取同组下一条记录的开始日期 sorted_df['next_start'] = sorted_df.groupby('sID')['date'].shift(-1) # 4. 计算结束日期 sorted_df['end_date'] = sorted_df.apply( lambda row: pd.to_datetime('2050-12-30') if pd.isna(row['next_start']) else row['next_start'] - pd.Timedelta(days=1), axis=1 ) # 5. 整理列顺序并排序 result = sorted_df.rename(columns={'date': 'start_date'})[['sID', 'Key', 'start_date', 'end_date']] result = result.sort_values(['sID', 'start_date'], ascending=[True, False]) # 打印结果 print(result)
运行后输出的结果和你要求的格式完全一致,其中BBB组的结果也会自动处理成连续不重叠的时间段。
内容的提问来源于stack exchange,提问作者koala
相关产品推荐
相关产品推荐

