I have this data of attendance from SQL Server that I must split into 2 columns (in and out).
Here is an example:
And here is the result that I want
Query:
CREATE TABLE [dbo].[Table1]
(
[ID] [varchar](50) NULL,
[DATETIME] [datetime] NULL,
[Flag] [int] NULL
)
INSERT INTO table1
VALUES ('ID-1', '2019-03-13 09:48:00.000', '2'),
('ID-1', '2019-03-13 09:48:00.000', '2'),
('ID-1', '2019-03-13 18:11:00.000', '3'),
('ID-1', '2019-03-13 18:11:00.000', '3'),
('ID-1', '2019-03-14 02:00:00.000', '3'),
('ID-1', '2019-03-14 09:54:00.000', '2'),
('ID-1', '2019-03-14 09:54:00.000', '2'),
('ID-1', '2019-03-14 09:54:00.000', '2'),
('ID-1', '2019-03-14 22:00:00.000', '3'),
('ID-1', '2019-03-14 22:00:00.000', '3'),
('ID-1', '2019-03-14 22:00:00.000', '3'),
('ID-1', '2019-03-15 13:55:00.000', '2'),
('ID-1', '2019-03-15 13:55:00.000', '2'),
('ID-1', '2019-03-15 13:55:00.000', '2'),
('ID-1', '2019-03-15 13:55:00.000', '2'),
('ID-1', '2019-03-15 13:55:00.000', '2'),
('ID-1', '2019-03-15 22:00:00.000', '3'),
('ID-1', '2019-03-15 22:00:00.000', '3'),
('ID-1', '2019-03-15 22:00:00.000', '3'),
('ID-1', '2019-03-15 22:00:00.000', '3')
Note:
The flag 2 means IN and 3 means OUT.
There can be more than one check in and check out so we must take the first in and last out.
There can be overtime so sometimes we must check the check out data from the next day.
How can I do this?
perhaps try a left join from Ins to outs, and find the earliest out time after that in-time.
sample below (untested):
WITH ins
AS ( SELECT *
FROM table1
WHERE Flag = 2 )
,outs
AS ( SELECT *
FROM table1
WHERE Flag = 3 )
SELECT i.ID
,i.DATETIME InTime
,MIN(o.DATETIME) OutTime
FROM ins i
LEFT JOIN outs o ON o.ID = i.ID AND o.DATETIME > i.DATETIME -- out must be later than in
GROUP BY i.ID
,i.DATETIME
,i.Flag;
The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.