Reputation: 153
I have three tables:
1) Calendar
2) Reading_Type
Reading_Type_ID
Type_Name
3) Readings
Reading_ID
Reading_Type_ID
Reading_Date
Reading
Only one entry is allowed for a given Reading_Type_ID
and Reading_Date
, but not all dates have a reading.
I need a query that returns all data from Readings
, plus yesterday's reading for that Reading_Type_ID
.
If the previous day (yesterday) has no reading, Yesterday_Reading
should be 0 (it should not just pull the reading from the previous row in the table if that row is > 1 day prior).
What I have so far:
SELECT
r.Reading_ID
, r.Reading_Type_ID
, r.Reading
, r.Reading_Date
, LAG(r.Reading, 1, 0)
OVER (PARTITION BY r.Reading_Type_ID ORDER BY r.Reading_Date)
AS Yesterday_Reading
FROM
Calendar c
LEFT JOIN
Readings r ON c.Date = r.Reading_Date
This LAG function pulls from the last row (by date) in the Readings
table, not strictly from "yesterday". I've tried some permutations (ORDER BY c.Date
, adding rows from c
to the SELECT
clause, etc), but I don't know how to fix this.
Upvotes: 0
Views: 4726
Reputation: 1269543
The problem is that you need the full calendar period for each Reading_Type_ID
. You can do this using a CROSS JOIN
:
SELECT r.Reading_ID, rr.Reading_Type_ID, r.Reading, r.Reading_Date,
LAG(r.Reading, 1, 0) OVER (PARTITION BY rr.Reading_Type_ID ORDER BY r.Reading_Date
) as Yesterday_Reading
FROM Calendar c CROSS JOIN
(SELECT DISTINCT r.Reading_Type_ID FROM Readings r) rr LEFT JOIN
Readings r
ON c.Date = r.Reading_Date AND r.Reading_Type_ID = rr.Reading_Type_ID;
Upvotes: 1