具有间隙的2个日期表的SQL连接(查找)

时间:2014-01-17 15:07:58

标签: sql join

更新

我添加了一个数据集示例,因此更容易解释我的问题。在我看来它是否是一个查询问题。

我有2013-01至2014-12所有月份的基准。我有一个查询表,每人的合同工作时间(列ID;例如,人1和人2)。

我必须将该基准月份与该月份的正确合约时数相匹配。查找表提供有关工作周时间变化的历史信息。

有人可以帮助我进行此加入或查找吗?

示例结果人1 :2013年4月(2013-04)的合约时数应为16小时。因为在查询表中他从2013-02-18开始工作了16个小时,并在2013-04-16开始工作了8个小时。

示例结果人2 :他的最后一次合同变更是2012-11-01至32小时。所以2013年的所有月份和2014年必须是32小时。


CREATE TABLE [dbo].[_Lookup](
    [ID] [int] NOT NULL,
    [Date] [nvarchar](50) NULL,
    [Hours] [int] NULL
) ON [PRIMARY]
GO
INSERT [dbo].[_Lookup] ([ID], [Date], [Hours]) VALUES (1, N'2013-01-01 00:00:00', 8)
INSERT [dbo].[_Lookup] ([ID], [Date], [Hours]) VALUES (1, N'2013-02-18 00:00:00', 16)
INSERT [dbo].[_Lookup] ([ID], [Date], [Hours]) VALUES (1, N'2013-04-16 00:00:00', 8)
INSERT [dbo].[_Lookup] ([ID], [Date], [Hours]) VALUES (1, N'2013-05-01 00:00:00', 32)
INSERT [dbo].[_Lookup] ([ID], [Date], [Hours]) VALUES (1, N'2013-09-15 00:00:00', 12)
INSERT [dbo].[_Lookup] ([ID], [Date], [Hours]) VALUES (1, N'2013-10-01 00:00:00', 20)
INSERT [dbo].[_Lookup] ([ID], [Date], [Hours]) VALUES (1, N'2015-01-01 00:00:00', 12)
INSERT [dbo].[_Lookup] ([ID], [Date], [Hours]) VALUES (2, N'2008-01-01 00:00:00', 24)
INSERT [dbo].[_Lookup] ([ID], [Date], [Hours]) VALUES (2, N'2009-03-01 00:00:00', 36)
INSERT [dbo].[_Lookup] ([ID], [Date], [Hours]) VALUES (2, N'2009-08-31 00:00:00', 24)
INSERT [dbo].[_Lookup] ([ID], [Date], [Hours]) VALUES (2, N'2010-02-01 00:00:00', 36)
INSERT [dbo].[_Lookup] ([ID], [Date], [Hours]) VALUES (2, N'2010-04-01 00:00:00', 30)
INSERT [dbo].[_Lookup] ([ID], [Date], [Hours]) VALUES (2, N'2011-08-01 00:00:00', 24)
INSERT [dbo].[_Lookup] ([ID], [Date], [Hours]) VALUES (2, N'2012-11-01 00:00:00', 32)


CREATE TABLE [dbo].[_Basetable](
    [ID] [int] NOT NULL,
    [Date] [datetime] NULL
) ON [PRIMARY]
GO
INSERT [dbo].[_Basetable] ([ID], [Date]) VALUES (1, CAST(0x0000A13900000000 AS DateTime))
INSERT [dbo].[_Basetable] ([ID], [Date]) VALUES (1, CAST(0x0000A15800000000 AS DateTime))
INSERT [dbo].[_Basetable] ([ID], [Date]) VALUES (1, CAST(0x0000A17400000000 AS DateTime))
INSERT [dbo].[_Basetable] ([ID], [Date]) VALUES (1, CAST(0x0000A19300000000 AS DateTime))
INSERT [dbo].[_Basetable] ([ID], [Date]) VALUES (1, CAST(0x0000A1B100000000 AS DateTime))
INSERT [dbo].[_Basetable] ([ID], [Date]) VALUES (1, CAST(0x0000A1D000000000 AS DateTime))
INSERT [dbo].[_Basetable] ([ID], [Date]) VALUES (1, CAST(0x0000A1EE00000000 AS DateTime))
INSERT [dbo].[_Basetable] ([ID], [Date]) VALUES (1, CAST(0x0000A20D00000000 AS DateTime))
INSERT [dbo].[_Basetable] ([ID], [Date]) VALUES (1, CAST(0x0000A22C00000000 AS DateTime))
INSERT [dbo].[_Basetable] ([ID], [Date]) VALUES (1, CAST(0x0000A24A00000000 AS DateTime))
INSERT [dbo].[_Basetable] ([ID], [Date]) VALUES (1, CAST(0x0000A26900000000 AS DateTime))
INSERT [dbo].[_Basetable] ([ID], [Date]) VALUES (1, CAST(0x0000A28700000000 AS DateTime))
INSERT [dbo].[_Basetable] ([ID], [Date]) VALUES (1, CAST(0x0000A2A600000000 AS DateTime))
INSERT [dbo].[_Basetable] ([ID], [Date]) VALUES (1, CAST(0x0000A2C500000000 AS DateTime))
INSERT [dbo].[_Basetable] ([ID], [Date]) VALUES (1, CAST(0x0000A2E100000000 AS DateTime))
INSERT [dbo].[_Basetable] ([ID], [Date]) VALUES (1, CAST(0x0000A30000000000 AS DateTime))
INSERT [dbo].[_Basetable] ([ID], [Date]) VALUES (1, CAST(0x0000A31E00000000 AS DateTime))
INSERT [dbo].[_Basetable] ([ID], [Date]) VALUES (1, CAST(0x0000A33D00000000 AS DateTime))
INSERT [dbo].[_Basetable] ([ID], [Date]) VALUES (1, CAST(0x0000A35B00000000 AS DateTime))
INSERT [dbo].[_Basetable] ([ID], [Date]) VALUES (1, CAST(0x0000A37A00000000 AS DateTime))
INSERT [dbo].[_Basetable] ([ID], [Date]) VALUES (1, CAST(0x0000A39900000000 AS DateTime))
INSERT [dbo].[_Basetable] ([ID], [Date]) VALUES (1, CAST(0x0000A3B700000000 AS DateTime))
INSERT [dbo].[_Basetable] ([ID], [Date]) VALUES (1, CAST(0x0000A3D600000000 AS DateTime))
INSERT [dbo].[_Basetable] ([ID], [Date]) VALUES (1, CAST(0x0000A3F400000000 AS DateTime))
INSERT [dbo].[_Basetable] ([ID], [Date]) VALUES (2, CAST(0x0000A13900000000 AS DateTime))
INSERT [dbo].[_Basetable] ([ID], [Date]) VALUES (2, CAST(0x0000A15800000000 AS DateTime))
INSERT [dbo].[_Basetable] ([ID], [Date]) VALUES (2, CAST(0x0000A17400000000 AS DateTime))
INSERT [dbo].[_Basetable] ([ID], [Date]) VALUES (2, CAST(0x0000A19300000000 AS DateTime))
INSERT [dbo].[_Basetable] ([ID], [Date]) VALUES (2, CAST(0x0000A1B100000000 AS DateTime))
INSERT [dbo].[_Basetable] ([ID], [Date]) VALUES (2, CAST(0x0000A1D000000000 AS DateTime))
INSERT [dbo].[_Basetable] ([ID], [Date]) VALUES (2, CAST(0x0000A1EE00000000 AS DateTime))
INSERT [dbo].[_Basetable] ([ID], [Date]) VALUES (2, CAST(0x0000A20D00000000 AS DateTime))
INSERT [dbo].[_Basetable] ([ID], [Date]) VALUES (2, CAST(0x0000A22C00000000 AS DateTime))
INSERT [dbo].[_Basetable] ([ID], [Date]) VALUES (2, CAST(0x0000A24A00000000 AS DateTime))
INSERT [dbo].[_Basetable] ([ID], [Date]) VALUES (2, CAST(0x0000A26900000000 AS DateTime))
INSERT [dbo].[_Basetable] ([ID], [Date]) VALUES (2, CAST(0x0000A28700000000 AS DateTime))
INSERT [dbo].[_Basetable] ([ID], [Date]) VALUES (2, CAST(0x0000A2A600000000 AS DateTime))
INSERT [dbo].[_Basetable] ([ID], [Date]) VALUES (2, CAST(0x0000A2C500000000 AS DateTime))
INSERT [dbo].[_Basetable] ([ID], [Date]) VALUES (2, CAST(0x0000A2E100000000 AS DateTime))


--  The result table should look like this:
--  
--  
--  ID  Date
--  1   2013-01-01  8
--  1   2013-02-01  8
--  1   2013-03-01  16
--  1   2013-04-01  16
--  1   2013-05-01  32
--  1   2013-06-01  32
--  1   2013-07-01  32
--  1   2013-08-01  32
--  1   2013-09-01  32
--  1   2013-10-01  20
--  1   2013-11-01  20
--  1   2013-12-01  20
--  1   2014-01-01  20  
--  1   2014-02-01  20  
--  1   2014-03-01  20  
--  1   2014-04-01  20  
--  1   2014-05-01  20  
--  1   2014-06-01  20  
--  1   2014-07-01  20  
--  1   2014-08-01  20  
--  1   2014-09-01  20  
--  1   2014-10-01  20  
--  1   2014-11-01  20  
--  1   2014-12-01  20  
--  2   2013-01-01  32
--  2   2013-02-01  32
--  2   2013-03-01  32
--  2   2013-04-01  32
--  2   2013-05-01  32
--  2   2013-06-01  32
--  2   2013-07-01  32
--  2   2013-08-01  32
--  2   2013-09-01  32
--  2   2013-10-01  32
--  2   2013-11-01  32
--  2   2013-12-01  32
--  2   2014-01-01  32
--  2   2014-02-01  32
--  2   2014-03-01  32

3 个答案:

答案 0 :(得分:1)

这对你有用吗?

WITH MyTimeDate ([Year], [Month], Hours_Work) AS
(
    SELECT 2013,    1,  8   UNION ALL
    SELECT 2013,    2,  16  UNION ALL
    SELECT 2013,    4,  8   UNION ALL
    SELECT 2013,    5,  32  UNION ALL
    SELECT 2013,    9,  12  UNION ALL
    SELECT 2013,    10, 20  UNION ALL
    SELECT 2015,    1,  12 
)
,MySampleCal ([Year], [Month]) AS
(
    SELECT 2013,    1   UNION ALL
    SELECT 2013,    2   UNION ALL
    SELECT 2013,    3   UNION ALL
    SELECT 2013,    4   UNION ALL
    SELECT 2013,    5   UNION ALL
    SELECT 2013,    6   UNION ALL
    SELECT 2013,    7   UNION ALL
    SELECT 2013,    8   UNION ALL
    SELECT 2013,    9   UNION ALL
    SELECT 2013,    10  UNION ALL
    SELECT 2013,    11  UNION ALL
    SELECT 2013,    12  
)
,DistanceCTE AS
(
    SELECT   C.[Year]
            ,C.[Month]
            ,D.Hours_Work
            ,DistanceSeq    = ROW_NUMBER() OVER (PARTITION BY C.[Year], C.[Month] ORDER BY D.[Month] - C.[Month] DESC)
    FROM MySampleCal    C
    JOIN MyTimeDate     D   ON  C.[Year] = D.[Year] 
                            AND C.[Month] >= D.Month 
)
SELECT *
FROM DistanceCTE
WHERE DistanceSeq = 1

答案 1 :(得分:0)

从您对问题的简短描述中我可以提供以下帮助

如果您在两个表上都有相同的ID,那么

SELECT b.Jaar, b.Maand, a.Jaar, a.Maand ,a.Hours_Work,ISNULL(SUM(b.Hours_Work),0) FROM b
LEFT JOIN a ON a.Key = b.Key

或根据Yearmonth

加入
SELECT b.Jaar, b.Maand, a.Jaar, a.Maand FROM s LEFT JOIN
a ON a.Hours_Work = b.Hours_Work and a.Jaar = b.Jaar and a.Maand = b.Month

希望它有所帮助。

如果没有,请说明。

答案 2 :(得分:0)

这就是答案:

Select    A.ID 
    , A.Date
    , (     Select Top 1 
                B.Hours
            From _Lookup B
            Where A.Date >= B.Date
                and A.Id = B.ID
            Order by B.Date desc
        ) as WorkingHours
From [_Basetable] A

感谢您帮助我!!