SQL Server,无法使用if else语句检查#temporary表是否存在

时间:2014-08-30 16:58:48

标签: sql-server tsql triggers exists temp-tables

我正在创建一个处理临时表(#attributeType)的触发器。由于触发器可以多次调用,我想确定并检查临时表#attributeType是否仍在那里。

这是我在触发器体中检查临时表的代码:

IF OBJECT_ID('tempdb..#attributeType') IS NOT NULL
    BEGIN
        DROP TABLE #attributeType
        SELECT * INTO #attributeType
        FROM attributeType
        PRINT 'IN IF'+   CAST(OBJECT_ID('tempdb..#attributeType') AS NVARCHAR(80))
    END
ELSE
    BEGIN
        SELECT * INTO #attributeType
        FROM attributeType
        PRINT 'IN ELSE'+  CAST(OBJECT_ID('tempdb..#attributeType') AS NVARCHAR(80))
    END

当我通过F5选择代码来测试代码时,我收到此错误消息,指出#attributeType临时表存在:

Msg 2714, Level 16, State 1, Line 11
There is already an object named '#attributeType' in the database.

我知道在存储过程中,一旦sp结束就会删除#tempTables,但我仍然无法理解为什么我的代码错了?

N.B。 当我注释掉ELSE块时代码可以工作。

2 个答案:

答案 0 :(得分:10)

您对OBJECT_ID('tempdb..#attributeType')的测试运行正常。您可以单独运行它,而不是同一批中的dropcreate来测试它。

问题是SQL Server在运行它之前解析整个批处理。如果它知道#attributeType存在,则会给出错误:

SELECT * INTO #attributeType

即使您将表格放在上一行中。

一种解决方案是将表放在另一批中:

IF OBJECT_ID('tempdb..#attributeType') IS NOT NULL
    DROP TABLE #attributeType
GO -- new batch
SELECT * INTO #attributeType ...

另一种解决方案是在不同的范围内创建表:

IF OBJECT_ID('tempdb..#attributeType') IS NOT NULL
    DROP TABLE #attributeType
exec ('SELECT * INTO #attributeType ...')

答案 1 :(得分:0)

如果您不需要在IF..ELSE语句中执行任何其他操作,您的代码可以简化为以下内容:

IF OBJECT_ID('tempdb..#attributeType') IS NOT NULL
BEGIN
    DROP TABLE #attributeType
END

SELECT *
INTO #attributeType
FROM attributeType

在这种情况下,您可以避免There is already an object named...错误,但仍然有临时表。