Sql 如果不存在,请查询一个表

Sql 如果不存在,请查询一个表,sql,sql-server,sql-server-2005,Sql,Sql Server,Sql Server 2005,我使用的是SQL 2005,代码如下: DECLARE @exist4 INT IF ( SELECT COUNT(*) existe FROM sysobjects obj WHERE obj.name = 'table4' ) > 0 BEGIN SET @exist4 = 1 END ELSE BEGIN SET @exist4 = 0 END /*now if table4 e

我使用的是SQL 2005,代码如下:

DECLARE @exist4 INT
IF ( SELECT COUNT(*) existe
     FROM   sysobjects obj
     WHERE  obj.name = 'table4'
   ) > 0 
    BEGIN 
        SET @exist4 = 1
    END
ELSE 
    BEGIN 
        SET @exist4 = 0
    END

/*now if table4 exist i need add to my query but if i do something as it
i got next error
Invalid object name 'table4'.*/


IF ( @exist4 = 0 ) 
    BEGIN

        SELECT  [table].col1 ,
                [table].col2 ,
                [table].col3 ,
                [table].colN
        FROM    [table] ,
                table2 ,
                table3
        WHERE   [table].id = table1.id
                AND table3.id = table2.id
    END
ELSE 
    BEGIN
        SELECT  [table].col1 ,
                [table].col2 ,
                [table].col3 ,
                [table].colN
        FROM    [table] ,
                table2 ,
                table3 ,
                table4
        WHERE   [table].id = table2.id
                AND table3.id = table2.id
                AND table4.id = table3.id
    END

当表4不存在时,此代码返回一个错误。如何才能使该查询正常工作?

发生的情况是,在解析查询时,表4不存在。这意味着您无法运行查询

您需要做的是延迟对该部分查询的解析,直到您知道存在表4为止

可以通过将查询放入字符串中,然后运行存储过程sp_excutesql来实现这一点。大概是这样的:

 DECLARE @myQueryString NVARCHAR(4000);
 SET @myQueryString = N'select table.col1, table.col2, table.col3, table.colN into #tmp
     from table,table2,table3,table4
     where table.id=table2.table1id 
     and table3.table2id=table2.id
     and table4.table3id=table3id';
 EXEC sp_executesql @myQueryString;

查询中引用表4的部分仅在第一次解析整个查询时作为字符串可用,因此解析器只看到一个字符串,而不是对各个表的引用。当您运行sp_executesql时,字符串将被解析并运行。由于您将它放在IF块中,它只会在知道table4存在时进行解析和运行。

优化器可能正在尝试评估select语句语法,所以将其包装在sp_executesql语句中以延迟该语法。尝试:

    IF ( SELECT OBJECT_ID('SQLInstances')
   ) IS NOT NULL 
    BEGIN 
        EXEC sp_executesql @statement = N'select table1.col1, table1.col2, table1.col3, table1.colN into #tmp from table1,table2,table3
where table1.id=table2.table1id 
and table3.table2id=table2.id'
    END
ELSE 
    BEGIN 
        EXEC sp_executesql @statement = N'select table1.col1, table1.col2, table1.col3, table1.colN into #tmp from table1,table2,table3,table4
where table1.id=table2.table1id 
and table3.table2id=table2.id
and table4.table3id=table3id'
    END

问题是什么?代码似乎有查询。顺便说一下,您应该使用正确的连接语法。逗号已过时。如果表存在,则该查询有效,但如果表不存在,则会出错。我编辑了你的问题,因此我认为它更清晰。检查编辑以确保我有正确的解释。它返回的错误是什么?这将创建tmp,然后在批处理结束后立即删除它。事实上,只要不执行语句,丢失的对象就不是问题。它将被推迟编译。e、 g.如果1=0,则从DOESNOTEXTIST选择*,否则从sys.objects选择*。运行良好。谢谢,但我没有名为sp_executesql的sp,我已经执行了exec@stationruns@angel-您确实有sp_executesql,但需要使用EXEC sp_executesql。EXEC部分仅对批处理中的第一条语句是可选的。但这对您没有帮助,因为只要语句执行且子作用域退出,它就会删除通过SELECT创建的临时表。。。是的,在这种情况下,tmp需要一个全局临时表