说我定义:
USE tempdb;
GO
CREATE TABLE [dbo].[Test1]
(
[ID] [INT] IDENTITY(1,1) NOT NULL PRIMARY KEY,
[DateString] [VARCHAR](max)
)
GO
INSERT INTO [dbo].[Test1](DateString) VALUES ('2014-10-20'),('BadDate');
GO
CREATE VIEW [dbo].[vw_Test1]
AS
SELECT
Id,
CONVERT(DATE,DateString) ConvertedDate
FROM dbo.Test1
WHERE isdate(DateString)=1
GO
以下查询正常工作:
SELECT * FROM [dbo].[vw_Test1]
以下查询引发" 从字符串"转换日期和/或时间时转换失败。
SELECT * FROM [dbo].[vw_Test1] WHERE ConvertedDate='2014-10-20'
显然这是因为条件ConvertedDate='2014-10-20'
在isdate(DateString)=1
之前执行。
你将如何修复vw_Test1以便它始终有效
答案 0 :(得分:1)
这取决于您使用的SQL Server版本。 SQL Server 2012+具有try_convert()
:
CREATE VIEW [dbo].[vw_Test1] as
SELECT Id, TRY_CONVERT(DATE, DateString) as ConvertedDate
FROM dbo.Test1
WHERE isdate(DateString) = 1;
如果转换失败,这将返回NULL
,而不是错误。
通常,SQL Server不保证评估select
组件的顺序。唯一的例外是case
语句 - 这是一个部分例外。无论如何,使用case
也可以解决问题:
CREATE VIEW [dbo].[vw_Test1] as
SELECT Id,
(CASE WHEN isdate(DateString) = 1 THEN CONVERT(DATE, DateString) END) as ConvertedDate
FROM dbo.Test1
WHERE isdate(DateString) = 1;
如果没有进行转换,则缺少ELSE
子句会强制NULL
。
答案 1 :(得分:0)
这种情况的一种方法是使用 CASE 语句,我认为您的观点 应该工作。
CREATE VIEW [dbo].[vw_Test1]
AS
SELECT
Id,
case ISDATE(DateString) when 1 then CONVERT(DATE,DateString) else 0 --oranything
end ConvertedDate
FROM dbo.Test1
WHERE isdate(DateString)=1
答案 2 :(得分:0)
如果您使用的是SQL Server 2012或更高版本,请尝试:
MS SQL Server 2012架构设置:
CREATE TABLE [dbo].[Test1]
(
[ID] [INT] IDENTITY(1,1) NOT NULL PRIMARY KEY,
[DateString] [VARCHAR](max)
);
GO
CREATE VIEW [dbo].[vw_Test1]
AS
SELECT
Id,
TRY_CONVERT(DATE,DateString) ConvertedDate
FROM dbo.Test1
WHERE isdate(DateString)=1;
GO
INSERT INTO [dbo].[Test1](DateString) VALUES ('2014-10-20'),('BadDate');
查询1 :
SELECT * FROM [dbo].[vw_Test1] WHERE ConvertedDate='2014-10-20'
<强> Results 强>:
| ID | CONVERTEDDATE |
|----|---------------|
| 1 | 2014-10-20 |