开发者

SQL Server: Most optimal way of storing time (without date)

开发者 https://www.devze.com 2023-03-25 10:13 出处:网络
Here\'s one more or less for perfection\'s sake. Microsoft SQL Server only contains the field type datetime for storing dates and times.

Here's one more or less for perfection's sake.

Microsoft SQL Server only contains the field type datetime for storing dates and times.

But let's say that I want to store a list of business hours, where the date is completely irrelevant. Currently I'm using the datetime type and then simply displaying the time-portion of the data. But I have two problems with this.

  1. It seems awkwardly inefficient.
  2. It may confuse future de开发者_开发百科velopers to see a full-blown date coming along with the time, which they may not know whether is used anywhere or not.

And so it begs the question; in the absence of a specific time field (like in MySQL), what is the most optimal way of storing only a particular time of day, from 00:00 to 23:59?

UPDATE: It's SQL Server 2005. (Also I'd just be interested in knowing what to do in general when there is no time type.)


For SQL Server 2005 or older...

If you only want to know to the minute, you can store it as an int in the range of 1-1440. 1 is 00:01 and 1440 is 0:00.

It would be easy do display as a time again if you like:

SELECT CAST((605 / 60) as varchar) + ':' + RIGHT('0' + CAST((605 % 60) as varchar), 2)

An additional advantage of this is that if you use a smallint data type you are saving 1-3 bytes per record from the built-in TIME datatype.

TIME uses 3-5 bytes per row and smallint is 2 bytes per row.

The extra bytes are for seconds and fractional seconds I believe.

EDIT

It's more complicated with seconds but still doable I should think...

1-86400 range (seconds per day)

DECLARE @i INT
SET @i = 3661

SELECT RIGHT('0' + CAST((@i / 3600) as varchar),2) --hours
+ ':' + RIGHT('0' + CAST((@i % 3600)/60 as varchar), 2) -- minutes
+ ':' + RIGHT('0' + CAST((@i % 3600)%60 as varchar), 2) -- seconds


SQL Server 2008 has a TIME datatype:

http://www.sql-server-performance.com/2007/datetime-2008/

DECLARE @dt as TIME
SET @dt = getdate()
PRINT @dt

Upgrade to SQL 2008?


MS SQL Server 2008 time data type


Personally I would not consider the points raised as sufficient enough to move away from using DATETIME or SMALLDATETIME.

  • An INT uses 4 bytes, as does a SMALLDATETIME
  • People make mistakes with SMALLINT that cause implicit type conversions (increasing cpu load)
  • Disk Space is cheap, you need a lot of bytes to add up to anythign significant
  • Code such as WHERE minutes < 720 is less understandable than WHERE time < '12:00'
  • Display issues (such as conversion of DATETIME to hh:mm) is often best place in the client
  • Using DATETIME allows future flexibility, such moving to seconds instead of minutes

That said, I have used INTEGER fields to hold number of seconds, such as when they're predominantly used for calculating average durations, etc.

My single biggest consideration in choosing the type is how the value will be used; to ensure legible code and performant execution plans.


SQL 2008 fixed this problem as others have noted but in 2005:

Do you need to perform any date math on the times? If not, you can store it as a string.

If you need to perform date math, a datetime with the day set to zero along with a descriptive column name shouldn't stump any future devs (and thanks for keeping us in mind).

And yes, datetime is clunky for time only storage but it functions just fine.

0

精彩评论

暂无评论...
验证码 换一张
取 消