2017-07-06 115 views
2

我想检测MS SQL DB中以'NAV'开头的数据库。我使用此代码试了一下:SQL错误 - 关键字'Database'附近的语法不正确

DECLARE @DBName NVARCHAR(MAX); 
SET @DBName = (SELECT name FROM master.dbo.sysdatabases where name LIKE '%NAV%'); 
EXECUTE ('USE' + @DBName); 

但我得到的错误信息:

Msg 156, Level 15, State 1, Line 1 
Incorrect syntax near the keyword 'Database'. 

知道什么是错的呢?

+1

这样做...'declare @sql varchar(4000)=('USE'+ @DBName); print(@sql)',你会发现你至少需要一个空间(假设查询只返回一个结果)。在尝试执行动态SQL之前打印动态SQL总是很好,因此您可以看到实际执行的内容。 – scsimon

+0

您是否在使用'sa'来运行该查询? – Alfabravo

+0

有关SQL Server的动态SQL问题的强制链接:http://www.sommarskog.se/dynamic_sql.html –

回答

2

把一个空间的使用后,把各地的数据库名称括号:

DECLARE @DBName NVARCHAR(MAX); 
SET @DBName = (SELECT name FROM master.dbo.sysdatabases where name LIKE '%NAV%'); 
EXECUTE ('USE [' + @DBName + ']'); 
+0

或者使用[QUOTENAME](https://docs.microsoft.com/zh-cn/sql/t-sql /函数/ quotename-transact-sql) – scsimon

3

我不知道在错误信息的关键字数据库,但我点问题: 您连接USE和没有空格的数据库名称:USENAV01不起作用。你应该使用'USE ' + QUOTENAME(@DBName)

其次,我不知道意图是什么,但是如果你做EXECUTE ('USE ' + @DBName);后跟其他(动态)查询,则会在你的当前连接上执行以下查询。换句话说,USE XXX对以下查询无关紧要。第三,正如Jesse在下面的评论中提到的那样;如果你有多个数据库,其中有一个name like '%NAV%'(你的问题就是这个建议),那么你的代码只能被其中一个数据库执行。没有order by,哪一个将是不可预测的。如果你想执行所有相关数据库的代码,你必须循环遍历它们。

+1

关于后续查询的很好的一点。我希望这是一个水落下的例子,动态sql更长,并且值得动态。 – scsimon

+1

除此之外,如果有超过1个数据库(如%NAV%),则此代码将因为您只能将一个分配给变量而中断。你必须使用一个临时表并循环来更精确。 – Jesse

+0

@Jesse,好点,补充回答。 – HoneyBadger

相关问题