讨论贴:在sp_executesql 中生成的临时表的可见性

首先创建数据表

IF object_id('TestTable') IS NOT NULL
    DROP TABLE TestTable
GO

CREATE TABLE TestTable(id INT IDENTITY(1,1),Info VARCHAR(10))
GO
INSERT TestTable SELECT 'a'
UNION ALL SELECT 'b'
GO

然后依次执行以下三个脚本

脚本一:

EXEC('SELECT * INTO #temp FROM TestTable')
SELECT * FROM #temp

脚本二:

exec SP_EXECUTESQL N'SELECT * INTO #temp FROM TestTable'
SELECT * FROM #temp

脚本三:

SELECT * INTO #temp FROM TestTable
EXEC('SELECT * FROM #temp')

--DROP TABLE #temp

执行后发现只有脚本三是成功的,其他连个脚本执行后都会提示:

Msg 208, Level 16, State 0, Line 2
Invalid object name '#temp'.

他们的不同支出就是sql语句执行的先后顺序,

我的理解是:

对数据库上下文所做的更改只在 exec sp_executesql,或者是exec('....') 语句结束前有效。

如果临时表在sp_executesql前就生成了,那么它是乐意接收的,如果是先执行了sp_executesql来创建临时表,

当这个语句执行结束后,临时表也随即消失了。

但是如果把#temp换成全局临时表##temp,三个脚本都可以正确返回。

期待听到更权威的解答。。。。。。

原文地址:https://www.cnblogs.com/wanglg/p/4158167.html