Follow along with the video below to see how to install our site as a web app on your home screen.
Note: This feature may not be available in some browsers.
--Create a table variable to hold our test data.
DECLARE @Times TABLE
(
EmployeeId INT,
WeekNumber INT,
HoursWorked INT
);
--Populate the table variable with the test data we are working with
INSERT INTO @Times (EmployeeId, WeekNumber, HoursWorked)
VALUES
(123, 1, 10), (123, 2, 10), (123, 3, 20), (123, 4, 40), (123, 5, 40), (123, 6, 40),
(123, 7, 40), (123, 8, 40), (234, 1, 20), (234, 2, 20), (234, 3, 25), (234, 4, 25),
(234, 5, 25), (234, 6, 25), (234, 7, 25), (234, 8, 25), (345, 1, 10), (345, 2, 30),
(345, 3, 15), (345, 4, 30), (345, 5, 40), (345, 6, 20), (345, 7, 25), (345, 8, 15);
--Read the table variable to ensure our raw data is accurate for our test cases
--SELECT
-- ti.EmployeeId,
-- ti.WeekNumber,
-- ti.HoursWorked
--FROM @Times ti;
--Create a table variable to hold the most recent 5 weeks for each employee.
--We will use this for further calcualtions/comparisons to get the final results
--If your employee count is large, this may be better served with a temp table
DECLARE @MostRecent5Weeks TABLE
(
EmployeeId INT,
WeekNumber INT,
HoursWorked INT
);
--Put the most recent five weeks for each employee into our table variable for use
--Order the records by the employee id and the week number in descending order so we get the newest weeks first
--Only keep the most recent 5 weeks for each employee
WITH cteMostRecentWeeks AS
(
SELECT
ti.EmployeeId,
ti.WeekNumber,
ti.HoursWorked,
RANK() OVER(PARTITION BY ti.EmployeeId ORDER BY ti.WeekNumber DESC) 'SortOrder'
FROM @Times ti
)
INSERT INTO @MostRecent5Weeks
(
EmployeeId,
WeekNumber,
HoursWorked
)
SELECT
mrw.EmployeeId,
mrw.WeekNumber,
mrw.HoursWorked
FROM cteMostRecentWeeks mrw
WHERE mrw.SortOrder <= 5;
--Read the table variable to ensure our data is accurate for our test cases
--SELECT
-- mr5w.EmployeeId,
-- mr5w.WeekNumber,
-- mr5w.HoursWorked
--FROM @MostRecent5Weeks mr5w;
--Create a table varibale to hold our comparisons
--SameHoursAsPreviousWeek typed as TINYINT to be able to SUM it later
DECLARE @Comparisons TABLE
(
EmployeeId INT,
WeekNumber INT,
HoursWorked INT,
SameHoursAsPreviousWeek TINYINT
);
--Populate the Comparisons table
--Uses LAG function to compare the values between the two records
INSERT INTO @Comparisons
(
EmployeeId,
WeekNumber,
HoursWorked,
SameHoursAsPreviousWeek
)
SELECT
mr5w.EmployeeId,
mr5w.WeekNumber,
mr5w.HoursWorked,
CASE
WHEN mr5w.HoursWorked = LAG(HoursWorked, 1, mr5w.HoursWorked) OVER (PARTITION BY mr5w.EmployeeId ORDER BY mr5w.WeekNumber) THEN 1
ELSE 0
END 'SameHoursAsPreviousWeek'
FROM @MostRecent5Weeks mr5w;
--Read the table variable to ensure our data is accurate for our test cases
--SELECT
-- co.EmployeeId,
-- co.WeekNumber,
-- co.HoursWorked,
-- co.SameHoursAsPreviousWeek
--FROM @Comparisons co;
--Our final query that gives us the expected results
--If the SUM of the SameHoursAsPreviousWeek = 5, the the last 5 weeks were the same
--If the SUM is less than 5, the last 5 weeks do not match and return a NULL
WITH cteSummaries AS
(
SELECT
co.EmployeeId,
MAX(co.WeekNumber) 'MostRecentWeek',
SUM(co.SameHoursAsPreviousWeek) 'NumberOfMatchingWeeks'
FROM @Comparisons co
GROUP BY
co.EmployeeId
)
SELECT
co.EmployeeId,
CASE
WHEN su.NumberOfMatchingWeeks = 5 THEN co.HoursWorked
ELSE NULL
END 'FinalHoursWorkedResult'
FROM @Comparisons co
INNER JOIN cteSummaries su
ON co.EmployeeId = su.EmployeeId
AND co.WeekNumber = su.MostRecentWeek;
SET NOCOUNT ON;
Declare @Temp Table(Employee Int, Week Int, Hours Int);
Insert Into @Temp Values(123,1,10)
Insert Into @Temp Values(123,2,10)
Insert Into @Temp Values(123,3,20)
Insert Into @Temp Values(123,4,40)
Insert Into @Temp Values(123,5,40)
Insert Into @Temp Values(123,6,40)
Insert Into @Temp Values(123,7,40)
Insert Into @Temp Values(123,8,40)
Insert Into @Temp Values(234,1,20)
Insert Into @Temp Values(234,2,20)
Insert Into @Temp Values(234,3,25)
Insert Into @Temp Values(234,4,25)
Insert Into @Temp Values(234,5,25)
Insert Into @Temp Values(234,6,25)
Insert Into @Temp Values(234,7,25)
Insert Into @Temp Values(234,8,25)
Insert Into @Temp Values(345,1,10)
Insert Into @Temp Values(345,2,30)
Insert Into @Temp Values(345,3,15)
Insert Into @Temp Values(345,4,30)
Insert Into @Temp Values(345,5,40)
Insert Into @Temp Values(345,6,20)
Insert Into @Temp Values(345,7,23)
Insert Into @Temp Values(345,8,15)
; With Data As
(
Select *,
Row_Number() Over (Partition By Employee Order BY Week DESC) As RowId
From @Temp
), DistinctHours As
(
Select Employee,
Count(Distinct Hours) As DistinctHours
From Data
Where RowId <= 5
Group By Employee
Having Count(Distinct Hours) = 1
)
Select Data.Employee,
Case When DistinctHours.DistinctHours = 1 Then Data.Hours End As Hours
From Data
Left Join DistinctHours
On Data.Employee = DistinctHours.Employee
Where RowId = 1