MCS*_*MCS 4 sql sql-server sql-server-2008
以下两个查询返回不同的结果.我理解差异与处理日期的时间部分的方式有关,但为什么它以这种方式工作?
// QUERY ONE
select top 3 OrderDate
from Orders
where OrderDate >= '2013-11-01 04:00'
and OrderDate <= '2013-11-30 05:00'
order by OrderDate
// RESULTS
// 2013-11-01
// 2013-11-01
// 2013-11-01
// QUERY TWO
exec sp_executesql
N'select top 3 OrderDate
from Orders
where OrderDate >= @p__linq__0
and OrderDate <= @p__linq__1
order by OrderDate',
N'@p__linq__0 datetime2(7),@p__linq__1 datetime2(7)',
@p__linq__0='2013-11-01T04:00:00',
@p__linq__1='2013-11-30T05:00:00'
// RESULTS
// 2013-11-02
// 2013-11-02
// 2013-11-02
Run Code Online (Sandbox Code Playgroud)
UPDATE
如果我将传递给sp_executesql的参数类型更改为"date"而不是"datetime",则结果是相同的.
// QUERY THREE
exec sp_executesql
N'select top 3 OrderDate
from Orders
where OrderDate >= @p__linq__0
and OrderDate <= @p__linq__1
order by OrderDate',
N'@p__linq__0 date,@p__linq__1 date',
@p__linq__0='2013-11-01T04:00:00',
@p__linq__1='2013-11-30T05:00:00'
// RESULTS
// 2013-11-01
// 2013-11-01
// 2013-11-01
Run Code Online (Sandbox Code Playgroud)
数据类型优先级是将表中的数据作为日期开始,并将其作为datetime2(7)进行比较.所以你的动态SQL版本实际上是这样运行的:
WHERE column_as_datetime2 >= @parameter_as_datetime2
Run Code Online (Sandbox Code Playgroud)
那么,既然2013-11-01 00:00:00.0000000是不大于或等于2013-11-01 04:00:00.0000000,从11月1日的行被排除在外.
最实用的解决方案是使用DATE参数(首选,因为参数应该与基础数据类型匹配,毕竟),和/或停止传递时间值以及它们.试试这些:
USE tempdb;
GO
CREATE TABLE dbo.Orders(OrderDate DATE);
INSERT dbo.Orders VALUES('2013-11-01'),('2013-11-01'),('2013-11-01'),
('2013-11-02'),('2013-11-02'),('2013-11-02');
exec sp_executesql N'select top 3 OrderDate
from Orders
where OrderDate >= @p__linq__0
and OrderDate <= @p__linq__1
order by OrderDate;
select top 3 OrderDate
from Orders
where OrderDate >= @p2
and OrderDate <= @p3
order by OrderDate;
select top 3 OrderDate
from Orders
where OrderDate >= @p4
and OrderDate <= @p5
order by OrderDate;',
N'@p__linq__0 datetime2(7),@p__linq__1 datetime2(7),
@p2 datetime2(7),@p3 datetime2(7),@p4 date,@p5 date',
@p__linq__0='2013-11-01T04:00:00',
@p__linq__1='2013-11-30T05:00:00',
@p2='2013-11-01T00:00:00', -- note no time
@p3='2013-11-30T00:00:00', -- note no time
@p4='2013-11-01',
@p5='2013-11-30';
Run Code Online (Sandbox Code Playgroud)
结果:
OrderDate
----------
2013-11-02
2013-11-02
2013-11-02
OrderDate
----------
2013-11-01
2013-11-01
2013-11-01
OrderDate
----------
2013-11-01
2013-11-01
2013-11-01
Run Code Online (Sandbox Code Playgroud)
| 归档时间: |
|
| 查看次数: |
789 次 |
| 最近记录: |