使用内部联接时重复行

时间:2015-03-20 06:39:50

标签: sql-server inner-join

我的表employeeLogs显示如下:

Emp_ID    Datetime                    State
0001      2015-03-19 10:44:40.000     LogIN
0002      2015-03-19 10:44:44.000     LogIN
0001      2015-03-19 10:44:49.000     LogOUT
1003      2015-03-19 10:44:54.000     LogIN
0002      2015-03-19 10:45:03.000     LogOUT
1003      2015-03-19 10:45:08.000     LogOUT
0001      2015-03-19 10:45:11.000     LogIN
0001      2015-03-19 15:12:30.000     LogOUT

我希望行LogIN和LogOut生成Column并执行各自的日期时间,我这样查询:

select distinct et.Emp_ID, f.LogIN, t.LogOUT from Emp_TimeLogs et

inner join

(

SELECT  distinct Emp_ID, [LogIN] , [LogOUT]
FROM 
    ( SELECT Emp_ID, 
             State,
             Date_Time  , 
            (ROW_NUMBER() OVER (ORDER BY Emp_ID DESC) ) AS RowNum         
      FROM Emp_TimeLogs et
   ) p 
PIVOT ( max(Date_Time)   
      FOR [state] IN ([LogIN],[LogOUT]) 
       ) AS pvt 
  WHERE DATENAME(Weekday,[LogIN]) <> 'Saturday'
) f on  
et.Emp_ID = f.Emp_ID
inner join 
(
SELECT  distinct Emp_ID, [LogIN] , [LogOUT]
       FROM 
    ( SELECT 
           Emp_ID, 
           State,
           Date_Time  , 
           (ROW_NUMBER() OVER (ORDER BY Emp_ID DESC) ) AS RowNum 
       FROM Emp_TimeLogs et     
    ) p 
    PIVOT ( max( Date_Time )
        FOR [state] IN ([LogIN],[LogOUT]) 
          ) AS pvt 
    WHERE DATENAME(Weekday,[LogOUT]) <> 'Saturday'
  ) t on  
et.Emp_ID = t.Emp_ID

但结果如下:

Emp_ID _____________LogIN________                   LogOUT

0001___    2015-03-19 10:44:40.000_____  2015-03-19 10:44:49.000  
0001___    2015-03-19 10:44:40.000_____  2015-03-19 15:12:30.000
0001___    2015-03-19 10:45:11.000_____  2015-03-19 10:44:49.000
0001___    2015-03-19 10:45:11.000_____  2015-03-19 15:12:30.000
0002___    2015-03-19 10:44:44.000_____  2015-03-19 10:45:03.000
1003___    2015-03-19 10:44:54.000_____  2015-03-19 10:45:08.000

Emp_ID重复或重复。

我希望得到这样的结果:

Emp_ID _____________LogIN________                   LogOUT

0001___    2015-03-19 10:44:40.000_____  2015-03-19 10:44:49.000
0001___    2015-03-19 10:45:11.000_____  2015-03-19 15:12:30.000
0002___    2015-03-19 10:44:44.000_____  2015-03-19 10:45:03.000
1003___    2015-03-19 10:44:54.000_____  2015-03-19 10:45:08.000

有什么解决方案吗?任何帮助将不胜感激!

1 个答案:

答案 0 :(得分:2)

我认为有一种更简单的方法可以得到你想要的东西:

SELECT Emp_ID, [LogIN], [LogOUT]
FROM (
   SELECT ROW_NUMBER() OVER (PARTITION BY Emp_ID, State ORDER BY Date_Time) AS rn,
          Emp_ID, Date_Time, State 
   FROM Emp_TimeLogs) p
PIVOT
(
   MAX (Date_Time)
   FOR State IN ( [LogIN], [LogOUT] )
) AS pvt

SQL Fiddle Demo

要解释这一点,PIVOT的源查询:

SELECT ROW_NUMBER() OVER (PARTITION BY Emp_ID, State ORDER BY Date_Time) AS rn, 
       Emp_ID, Date_Time, State 
FROM Emp_TimeLogs
ORDER BY Emp_ID, Date_Time

生成以下结果集:

rn  Emp_ID  Date_Time               State
--------------------------------------------
1   0001    2015-03-19 10:44:40.000 LogIN
1   0001    2015-03-19 10:44:49.000 LogOUT
2   0001    2015-03-19 10:45:11.000 LogIN
2   0001    2015-03-19 15:12:30.000 LogOUT
1   0002    2015-03-19 10:44:44.000 LogIN
1   0002    2015-03-19 10:45:03.000 LogOUT
1   1003    2015-03-19 10:44:54.000 LogIN
1   1003    2015-03-19 10:45:08.000 LogOUT

通过为每个(LogINLogOUT)对旋转(rnEmp_ID)对来生成交叉表。