I have an INT column in my table. This column stores the date in special format. I'm trying to convert that column to DATE type.
For example, we keep '2016-03-14'
as 20160314
.
The exception is, for the last of each month, we do not store day.
So for '2016-03-31'
we store 201603
and I have to consider if the number is less than 999999
or not to find is the number represents a month-end or other days in month.
So far, I have 2 queries to achieve this task:
Query 1:
This is all mathematics formula.
declare @k int = 20160321
--declare @k int = 201603
select
IIF(@k < 999999
, EOMONTH(DATEFROMPARTS(@k /100, @k % 100, 1), 0)
, DATEFROMPARTS(@k /10000, (@k / 100) % 100, @k % 100)
)
Query 2: This one is using string manipulation.
declare @k int = 20160321
--declare @k int = 201603
select
IIF(@k < 999999
, EOMONTH(cast(LEFT(@k, 4) + '-' + RIGHT(@k, 2) + '-01' as date), 0)
, cast(LEFT(@k, 4) + '-' + RIGHT(LEFT(@k, 6), 2) + '-' + RIGHT(@k, 2) as date )
) AS DateColumn
I need to do the conversion formulas in WHERE
clause. Something like:
SELECT K, Dt, Name -- and more fields
FROM tbl
WHERE IIF(K < 999999
, EOMONTH(DATEFROMPARTS(K /100, K % 100, 1), 0)
, DATEFROMPARTS(K /10000, (K / 100) % 100, K % 100)
) < GetDate()
And performance is important
Question: Is there a better way to do this? Possibly a ways that SQL Server can use the clustered index I have on K column.