1.关于字符型和DATETIME类型的转化
由于时间类型的优先级高于字符型,所以当比较一个DATETIME类型的数据和一个字符串的时候,字符串首先会转化成DATETIME类型。
A '20060102' '090807' '20090203 12:11:11.111'转化成时间类型的时候
B '2009-02-03 12:11:11.111'转化成时间类型的时候
不受会话语言设置影响(SET LANGUAGE) 注意B类型转换的时候不讷讷个省略它的时间部分。
2.字符型和DATETIME类型转换精度问题
--字符串转化成datetime ,转化后的时间比字符串慢了1毫秒,这是因为自动舍入到最近的百分之三秒
declare @s varchar(100)
set @s='2005-09-23 03:23:43:001'
SELECT CAST(@s AS datetime)
/*
-----------------------
2005-09-23 03:23:43.000
*/
-------------------------
--字符串转化成smalldatetime ,转化后的时间比字符串快了大约秒,这是因为自动舍入到最近的分钟数
declare @s varchar(100)
set @s='2005-09-23 03:23:43:001'
SELECT CAST(@s AS Smalldatetime)
/*
-----------------------
2005-09-23 03:24:00
*/
------------------
还要注意 它们之间的转化并不是什么简单的截断数据 有精确到毫秒时候 毫秒部分匹配【0-9】【0-9】【037】
SQL SERVER 有时候无法精确表示某个时间的瞬间,比如‘20090202 23:59:59.999’,自动舍入为
‘20090203 00:00:00.000’
declare @s table (dates datetime)
insert @s
select '20090211 00:00:00.000' union all
select '20090212 00:00:00.000'
select * from @s
where dates between '20090211 00:00:00:000' and '20090211 23:59:59.999' --转化成-02-12 00:00:00.000
/*
dates
-----------------------
2009-02-11 00:00:00.000
2009-02-12 00:00:00.000
*/
select * from @s
where dates >='20090211' and dates< '20090212' --SARG,优化器考虑使用Index Seek
---------------
2009-02-11 00:00:00.000
*/
select * from @s
where convert(varchar(8),dates,112)='20090211'
/*
Dates
-----------------------
2009-02-11 00:00:00.000
*/
3.Datetime和SmallDatetime类型的内部存储
时间类型在存储时候被分成2日期和时间2独立部分.
日期部分存储的是和1900-01-01的天数差,时间部分存储,如果是Datetime,午夜0点后时钟周期数,一个时钟周期数为1/300秒,即3.33毫秒.如果是smalldatetime,时间部分存储的是午夜0点以后的分钟数.
我们只要将时间转换成16进制就可以很清楚的看到了。接下来演示一下:
declare @day1 datetime
set @day1=current_timestamp
--datetime
select @day1,--2010-03-07 17:29:49.637
CONVERT(varbinary(8),@day1),-- 0x00009D32012057FB
CONVERT(int,SUBSTRING(CONVERT(varbinary(8),@day1),1,4)),--40242
CONVERT(int,SUBSTRING