0

我正在使用 SQL Server (2008) 并且似乎无法在 IIF 语句的布尔部分中使用 LIKE 语句。

以下查询运行正确,因此我的 LIKE 语句的语法看起来不错:

SELECT *
FROM dbo.IpPbxCDR
WHERE dbo.IpPbxCDR.OriginationNumber LIKE '+31%'

但是,在运行以下查询时:

SELECT *
FROM dbo.IpPbxCDR
WHERE IIF(dbo.IpPbxCDR.OriginationNumber LIKE '+31%','0' + Right([dbo.IpPbxCDR].[OriginationNumber],9), Replace([dbo.IpPbxCDR].[OriginationNumber],'+','00')) = '0201234567'

我收到以下错误:关键字“LIKE”附近的语法不正确。

我做错了什么,还是我在 SQL Server 2008 上做不到?

哦,另一件事,如果我将表添加为 Access 中的链接表,并在那里运行查询,一切正常,但是我认为在这种情况下,Access 会进行评估而不是 SQL Server。

编辑:(已解决)好吧,看起来在 2012 版之前需要使用 Case 语句。一如既往,感谢您输入的 stackoverflow 用户,你们都很棒!

4

1 回答 1

3

您可以使用CASE 表达式

SELECT  *
FROM    dbo.IpPbxCDR
WHERE   CASE WHEN dbo.IpPbxCDR.OriginationNumber LIKE '+31%'
            THEN '0' + Right(dbo.IpPbxCDR.OriginationNumber,9)
            ELSE Replace(dbo.IpPbxCDR.OriginationNumber,'+','00'))
        END = '0201234567';

注意我已经替换[dbo.IpPbxCDR]为就像dbo.IpPbxCDR这将寻找一个名为dbo.IpPbxCDR而不是IpPbxCDRdbo模式中调用的表的表。


附录

我不知道它是否适用,但上面不会使用您可能拥有的任何索引OriginationNumber,如果您在 select 中使用表达式,这很好,但在 where 子句中可能会导致性能问题. 要使用索引,您可以重写如下:

DECLARE @Number VARCHAR(10) = '0201234567';

SELECT  *
FROM    dbo.IpPbxCDR
WHERE   OriginationNumber = CASE WHEN @Number LIKE '00%' THEN STUFF(@Number, 1, 2, '+') ELSE STUFF(@Number, 1, 1, '+31') END;

这会对常量进行所有操作,因此只进行一次,而不是对每一行执行函数。为了进行比较,这是运行 ablve(顶部)与第一个查询(底部)相比时的执行计划:

在此处输入图像描述

测试模式

CREATE TABLE dbo.IpPbxCDR (OriginationNumber VARCHAR(15));
INSERT dbo.IpPbxCDR (OriginationNumber)
VALUES ('+31201234567'), ('+3469694535'), ('+44208979754');

INSERT dbo.IpPbxCDR (OriginationNumber)
SELECT  TOP 10000 '+312012' + RIGHT('0000' + CAST(ROW_NUMBER() OVER(ORDER BY a.Object_ID) AS VARCHAR(5)), 5)
FROM    sys.all_objects a
        CROSS JOIN sys.all_objects b
UNION ALL
SELECT  TOP 10000 '+342012' + RIGHT('0000' + CAST(ROW_NUMBER() OVER(ORDER BY a.Object_ID) AS VARCHAR(5)), 5)
FROM    sys.all_objects a
        CROSS JOIN sys.all_objects b
UNION ALL
SELECT  TOP 10000 '+332012' + RIGHT('0000' + CAST(ROW_NUMBER() OVER(ORDER BY a.Object_ID) AS VARCHAR(5)), 5)
FROM    sys.all_objects a
        CROSS JOIN sys.all_objects b

CREATE NONCLUSTERED INDEX IX_IpPbxCDR_OriginationNumber ON dbo.IpPbxCDR (OriginationNumber);
于 2013-10-21T13:05:25.560 回答