Sql server 如何跨两个表(脏)配对日期时间

Sql server 如何跨两个表(脏)配对日期时间,sql-server,tsql,datetime,Sql Server,Tsql,Datetime,我正在看一个SQL Server 2008数据库,它有两个表,每个表都有一个PK(INT)列和一个DateTime列 表之间没有明确的关系,但我知道应用程序有一种启发式倾向,即成对插入数据库,每个表插入一行,日期时间似乎永远不会完全匹配,但通常非常接近 我试图通过在另一个表中查找最接近的匹配日期时间来备份每个表中的PKs。对于此匹配,每个PK只能使用一次 最好的方法是什么 编辑:对不起,请在底部找到一些示例输入和所需输出 +-------+-------------------------+ |

我正在看一个SQL Server 2008数据库,它有两个表,每个表都有一个PK(INT)列和一个DateTime列

表之间没有明确的关系,但我知道应用程序有一种启发式倾向,即成对插入数据库,每个表插入一行,日期时间似乎永远不会完全匹配,但通常非常接近

我试图通过在另一个表中查找最接近的匹配日期时间来备份每个表中的PKs。对于此匹配,每个PK只能使用一次

最好的方法是什么

编辑:对不起,请在底部找到一些示例输入和所需输出

+-------+-------------------------+
| t1.PK |       t1.DateTime       |
+-------+-------------------------+
|     1 | 2016-08-11 00:11:03.000 |
|     2 | 2016-08-11 00:11:08.000 |
|     3 | 2016-08-11 11:03:00.000 |
|     4 | 2016-08-11 11:08:00.000 |
+-------+-------------------------+

+-------+-------------------------+
| t2.PK |       t2.DateTime       |
+-------+-------------------------+
|     1 | 2016-08-11 11:02:00.000 |
|     2 | 2016-08-11 00:11:02.000 |
|     3 | 2016-08-11 22:00:00.000 |
|     4 | 2016-08-11 11:07:00.000 |
|     5 | 2016-08-11 00:11:07.000 |
+-------+-------------------------+

+-------+-------+-------------------------+-------------------------+
| t1.PK | t2.PK |       t1.DateTime       |       t2.DateTime       |
+-------+-------+-------------------------+-------------------------+
|     1 |     2 | 2016-08-11 00:11:03.000 | 2016-08-11 00:11:02.000 |
|     2 |     5 | 2016-08-11 00:11:08.000 | 2016-08-11 00:11:07.000 |
|     3 |     1 | 2016-08-11 11:03:00.000 | 2016-08-11 11:02:00.000 |
|     4 |     4 | 2016-08-11 11:08:00.000 | 2016-08-11 11:07:00.000 |
+-------+-------+-------------------------+-------------------------+

连接到
t1.DateTime
t2.DateTime
之间DATEDIFF(以秒为单位)最低的行。通过将表1与表2交叉连接,然后根据Tab Alleman的建议获得以秒为单位的日期差,可以获得所需的结果。下一步是使用
ROW\u NUMBER()
函数对每个匹配项进行排序。最后一步是只选择
Rank=1
的行。 以下示例演示如何使用示例数据:

DECLARE @t1 TABLE
(
     ID         INT PRIMARY KEY
    ,[DateTime] DATETIME
);

DECLARE @t2 TABLE
(
    ID          INT PRIMARY KEY
    ,[DateTime] DATETIME
)

INSERT INTO @t1
(
     ID         
    ,[DateTime]
)
VALUES
(1 ,'2016-08-11 00:11:03.000'),
(2 ,'2016-08-11 00:11:08.000'),
(3 ,'2016-08-11 11:03:00.000'),
(4 ,'2016-08-11 11:08:00.000');

INSERT INTO @t2
(
     ID         
    ,[DateTime]
)
VALUES
(1, '2016-08-11 11:02:00.000'),
(2, '2016-08-11 00:11:02.000'),
(3, '2016-08-11 22:00:00.000'),
(4, '2016-08-11 11:07:00.000'),
(5, '2016-08-11 00:11:07.000');


WITH CTE_DateDifference
AS
(
    SELECT      t1.ID AS T1_ID
                ,t2.ID AS T2_ID
                ,t1.[DateTime] AS T1_DateTime
                ,t2.[DateTime] AS T2_DateTime
                ,ABS(DATEDIFF(SECOND, t1.[DateTime], t2.[DateTime])) AS Duration    -- Determine the difference between the dates in seconds.
    FROM        @t1 t1
    CROSS JOIN  @t2 t2
),CTE_RankDateMatch
AS
(
    SELECT  T1_ID
            ,T2_ID
            ,T1_DateTime
            ,T2_DateTime
            ,ROW_NUMBER() OVER (PARTITION BY T1_ID ORDER BY Duration) AS [Rank]  -- Rank each match, the row numbers generated will be order based on the duration between the dates.   Thus rows with a number of 1will be the closest match between the two tables.   
    FROM    CTE_DateDifference
)
-- Finally select out the rows with a Rank equal to 1.
SELECT  *   
FROM    CTE_RankDateMatch
WHERE   [Rank] = 1

从t1连接t1.datetimecolumn上的t2,介于dateadd(分钟,-1,t2.datetimecolumn)和dateadd(分钟,1,t2.datetimecolumn)之间@AaronBertrand感谢您的快速回复,但很抱歉我不够清楚。我用一些示例输入和期望的输出澄清了这个问题。