校园春色亚洲色图_亚洲视频分类_中文字幕精品一区二区精品_麻豆一区区三区四区产品精品蜜桃

主頁 > 知識庫 > 淺析SQL Server的嵌套存儲過程中使用同名的臨時表怪像

淺析SQL Server的嵌套存儲過程中使用同名的臨時表怪像

熱門標簽:南京電銷外呼系統哪家好 地圖標注如何弄全套標 外呼系統會封嗎 股票配資電銷機器人 實體店地圖標注怎么標 電銷機器人 深圳 武漢AI電銷機器人 在電子版地圖標注要收費嗎 萬利達綜合醫院地圖標注點

SQL Server的嵌套存儲過程,外層存儲過程和內層存儲過程(被嵌套調用的存儲過程)中可以存在相同名稱的本地臨時表嗎?如果可以的話,那么有沒有什么問題或限制呢? 在嵌套存儲過程中,調用的是外層存儲過程的臨時表還是自己定義的臨時表呢? 是否類似高級語言的變量一樣,本地臨時表有沒有“作用域“范圍呢?

注意:也可以稱呼為父存儲過程和子存儲過程,外層存儲過程和內層存儲過程。這些只是不同的稱呼或叫法而已。我們這里統一使用外層存儲過程和內層存儲過程。后續文章部分不再述說。

我們先來看一個例子,如下所示,我們構造一個簡單的例子。

IF EXISTS (SELECT 1 FROM sys.objects WHERE object_id = OBJECT_ID(N'dbo.PRC_TEST') AND OBJECTPROPERTY(object_id, 'IsProcedure') =1)
BEGIN
  DROP PROCEDURE dbo.PRC_TEST
END
GO
CREATE PROC dbo.PRC_TEST
AS
BEGIN
 
  CREATE TABLE #tmp_test(id INT);
 
  INSERT INTO #tmp_test
  SELECT 1;
 
  SELECT * FROM #tmp_test;
 
  EXEC PRC_SUB_TEST
 
  SELECT * FROM #tmp_test
  
 
END
GO
 
IF EXISTS(SELECT 1 FROM sys.objects WHERE object_id= OBJECT_ID(N'dbo.PRC_SUB_TEST' ) AND OBJECTPROPERTY(object_id, 'IsProcedure')=1)
BEGIN
  DROP PROCEDURE dbo.PRC_SUB_TEST;
END
GO
 
CREATE PROCEDURE dbo.PRC_SUB_TEST
AS
BEGIN
  
  CREATE TABLE #tmp_test(name VARCHAR(128));
 
  INSERT INTO #tmp_test
  SELECT name FROM sys.objects
 
  SELECT * FROM #tmp_test;
END
GO
 
EXEC PRC_TEST;

簡單測試似乎正常,并沒有發現什么問題。如果此時你就下一個結論的話,那么就為時過早了! 打個比方,你看見一只天鵝是白色的,如果你下了一個定論:“所有天鵝都是白色的”,其實這個世界真的有黑天鵝,只是你沒有見過而已!如下所示,我們修改一下存儲過程dbo.PRC_SUB_TEST,使用字段名name替換*,如下所示:

IF EXISTS(SELECT 1 FROM sys.objects WHERE object_id= OBJECT_ID(N'dbo.PRC_SUB_TEST' ) AND OBJECTPROPERTY(object_id, 'IsProcedure')=1)
BEGIN
  DROP PROCEDURE dbo.PRC_SUB_TEST;
END
GO
 
CREATE PROCEDURE dbo.PRC_SUB_TEST
AS
BEGIN
  
  CREATE TABLE #tmp_test(name VARCHAR(128));
 
  INSERT INTO #tmp_test
  SELECT name FROM sys.objects
 
  SELECT name FROM #tmp_test;
END
GO

然后重復上面測試,如下所示,此時執行存儲過程dbo.PRC_TEST的話,就會報錯:“Invalid column name 'name'.”

此時只要先我執行一次存儲過程dbo.PRC_SUB_TEST,然后再去執行存儲過程dbo.PRC_TEST就不會報錯了。而且只要執行過一次這個存儲過程,然后在當前會話或其它任何會話執行dbo.PRC_TEST都不會報錯了。是否非常讓人迷惑或不解。

EXEC dbo.PRC_SUB_TEST;
 
EXEC PRC_TEST;

如果你要再次重現這個現象的話,只能通過下面SQL或者刪除/重建存儲過程的方式,才能重現這個現象。似乎有點幽靈現象的感覺。

DBCC FREEPROCCACHE

關于這個現象,官方文檔(詳見參考資料的鏈接地址)有這么一段描述:

A local temporary table created within a stored procedure or trigger can have the same name as a temporary table that was created before the stored procedure or trigger is called. However, if a query references a temporary table and two temporary tables with the same name exist at that time, it is not defined which table the query is resolved against. Nested stored procedures can also create temporary tables with the same name as a temporary table that was created by the stored procedure that called it. However, for modifications to resolve to the table that was created in the nested procedure, the table must have the same structure, with the same column names, as the table created in the calling procedure. This is shown in the following example.

在存儲過程或觸發器中創建的本地臨時表的名稱可以與在調用存儲過程或觸發器之前創建的臨時表名稱相同。 但是,如果查詢引用臨時表,而同時有兩個同名的臨時表,則不定義針對哪個表解析該查詢。 嵌套存儲過程同樣可以創建與調用它的存儲過程所創建的臨時表同名的臨時表。但是,為了對其進行修改以解析為在嵌套過程中創建的表,此表必須與調用過程創建的表具有相同的結構和列名。下面的示例說明了這一點。

CREATE PROCEDURE dbo.Test2
AS
  CREATE TABLE #t(x INT PRIMARY KEY);
  INSERT INTO #t VALUES (2);
  SELECT Test2Col = x FROM #t;
GO
 
CREATE PROCEDURE dbo.Test1
AS
  CREATE TABLE #t(x INT PRIMARY KEY);
  INSERT INTO #t VALUES (1);
  SELECT Test1Col = x FROM #t;
EXEC Test2;
GO
 
CREATE TABLE #t(x INT PRIMARY KEY);
INSERT INTO #t VALUES (99);
GO
 
EXEC Test1;
GO

官方文檔中“同時有兩個同名的臨時表,則不定義針對哪個表解析該查詢”這種闡述感覺還是讓人有點迷糊。這里簡單解釋一下,在存儲過程的嵌套調用中,允許外層過程和內層存儲過程中存在相同名字的本地臨時表,但是在內存過程中,如果要對其進行修改或解析(修改很好理解,例如新增索引,增加字段等這類DDL操作;關于解析,查詢臨時表,SQL中指定字段名,就需要解析resolve),那么此時這個臨時表必須表結構一致,否則就會報錯。官方文檔,就是這么一句話,告訴你不行,但是具體原因沒有說。那么我們不妨做一些推測,在存儲過程的嵌套調用中,是否創建了兩個本地臨時表呢?有沒有可能實際只創建了一個本地臨時表呢?出現本地臨時表重用的情況呢? 那么我們簡單驗證一下,如下所示,這里可以判斷實際上創建了兩個本地臨時表。并沒有出現臨時表重用的情況。

SELECT * 
FROM sys.dm_os_performance_counters
WHERE counter_name LIKE 'Temp Tables Creation Rate%';
 
EXEC PRC_TEST;
 
SELECT * 
FROM sys.dm_os_performance_counters
WHERE counter_name LIKE 'Temp Tables Creation Rate%';

當然你可以用下面SQL來進行驗證,跟上面驗證的結果一致。

IF EXISTS(SELECT 1 FROM sys.objects WHERE object_id= OBJECT_ID(N'dbo.PRC_SUB_TEST' ) AND OBJECTPROPERTY(object_id, 'IsProcedure')=1)
BEGIN
  DROP PROCEDURE dbo.PRC_SUB_TEST;
END
GO
 
 
CREATE PROCEDURE dbo.PRC_SUB_TEST
AS
BEGIN
  
  SELECT * FROM #tmp_test;
 
  SELECT * FROM tempdb.dbo.sysobjects WHERE name LIKE '#tmp_test%'
  CREATE TABLE #tmp_test(name VARCHAR(128));
 
  INSERT INTO #tmp_test
  SELECT name FROM sys.objects
  SELECT * FROM tempdb.dbo.sysobjects WHERE name LIKE '#tmp_test%'
  SELECT * FROM #tmp_test;
END
GO

然后我們來看看臨時表的“作用域”,抱歉我用這么一個概念,官方文檔是沒有這個概念,這個只是我們思考的一個方面,細節方面沒有必要抬杠。如下所示,我們修改一下存儲過程

IF EXISTS(SELECT 1 FROM sys.objects WHERE object_id= OBJECT_ID(N'dbo.PRC_SUB_TEST' ) AND OBJECTPROPERTY(object_id, 'IsProcedure')=1)
BEGIN
  DROP PROCEDURE dbo.PRC_SUB_TEST;
END
GO
CREATE PROCEDURE dbo.PRC_SUB_TEST
AS
BEGIN
  
  SELECT * FROM #tmp_test;
  CREATE TABLE #tmp_test(name VARCHAR(128));
 
  INSERT INTO #tmp_test
  SELECT name FROM sys.objects
 
  SELECT * FROM #tmp_test;
END
GO

通過實驗驗證,我們發現外層存儲過程的臨時表在內層存儲過程中有效,它的“作用域”是在內層存儲過程的同名臨時表創建之前,這個跟高級語言中的全局變量和局部變量作用域有點類似。

既然創建了兩個本地臨時表,那么為什么修改或解析的時候就會報錯呢? 個人的一個猜測是,優化器解析過后,在執行過程中,解析或修改的時候,數據庫引擎無法判斷或者代碼里面沒有這種邏輯去控制檢索哪一個臨時表。有可能是代碼里面的一個缺陷亦或是某種邏輯原因導致。上述僅僅是個人的一個猜測、推理。如有不足或不對的地方,敬請指正。

參考資料:

https://docs.microsoft.com/zh-cn/previous-versions/sql/sql-server-2012/ms174979(v=sql.110)?redirectedfrom=MSDN

到此這篇關于淺析SQL Server的嵌套存儲過程中使用同名的臨時表怪像的文章就介紹到這了,更多相關SQL Server嵌套存儲過程內容請搜索腳本之家以前的文章或繼續瀏覽下面的相關文章希望大家以后多多支持腳本之家!

您可能感興趣的文章:
  • sqlserver2005利用臨時表和@@RowCount提高分頁查詢存儲過程性能示例分享
  • sql server2008調試存儲過程的完整步驟
  • SQLServer2008存儲過程實現數據插入與更新
  • Sql Server 存儲過程調用存儲過程接收輸出參數返回值
  • SQLServer存儲過程創建和修改的實現代碼
  • 獲取SqlServer存儲過程定義的三種方法
  • SqlServer存儲過程實現及拼接sql的注意點

標簽:武威 廣東 泰安 汕頭 濟寧 濟源 臺州 安徽

巨人網絡通訊聲明:本文標題《淺析SQL Server的嵌套存儲過程中使用同名的臨時表怪像》,本文關鍵詞  淺析,SQL,Server,的,嵌套,存儲,;如發現本文內容存在版權問題,煩請提供相關信息告之我們,我們將及時溝通與處理。本站內容系統采集于網絡,涉及言論、版權與本站無關。
  • 相關文章
  • 下面列出與本文章《淺析SQL Server的嵌套存儲過程中使用同名的臨時表怪像》相關的同類信息!
  • 本頁收集關于淺析SQL Server的嵌套存儲過程中使用同名的臨時表怪像的相關信息資訊供網民參考!
  • 推薦文章
    校园春色亚洲色图_亚洲视频分类_中文字幕精品一区二区精品_麻豆一区区三区四区产品精品蜜桃
    久久九九久久九九| 91美女片黄在线| 欧美一区二区视频免费观看| 色天天综合色天天久久| 91视频在线看| 亚洲欧美另类在线| 三级不卡在线观看| 日韩电影免费在线观看网站| 国产精品中文欧美| 日本高清视频一区二区| 日韩精品一区二区在线观看| 日韩欧美资源站| 精品国产一区二区三区久久影院| 国产精品全国免费观看高清 | 成人国产精品免费观看动漫| 91精品国产美女浴室洗澡无遮挡| 免费成人在线观看视频| 欧美色图在线观看| 国产精品自拍一区| 综合av第一页| 99久久99久久精品免费观看| 久久婷婷成人综合色| 麻豆极品一区二区三区| 欧美性猛交xxxx乱大交退制版| 日韩福利电影在线观看| 国产精品久久久久一区二区三区 | 天堂va蜜桃一区二区三区| 久久免费国产精品| 激情久久五月天| 日韩一二三区不卡| 成人91在线观看| 麻豆久久久久久| 亚洲高清免费视频| 99久久伊人精品| 久草这里只有精品视频| 欧美一区二区三区免费在线看| 成人午夜av电影| 亚洲视频一区二区在线观看| 精品sm在线观看| 56国语精品自产拍在线观看| 日本女优在线视频一区二区| 国产精品久久久久影院色老大| 欧美mv和日韩mv的网站| 污片在线观看一区二区| 欧美日本韩国一区二区三区视频| 舔着乳尖日韩一区| 亚洲乱码国产乱码精品精可以看| 91论坛在线播放| 成人黄色一级视频| 国产福利91精品| 一区二区三区高清| 69久久夜色精品国产69蝌蚪网| 91亚洲国产成人精品一区二区三 | 亚洲一区二区视频在线观看| 99精品偷自拍| 国产99一区视频免费| 亚洲女与黑人做爰| 国产精品国产三级国产有无不卡 | 国产99久久久精品| 国产成人久久精品77777最新版本 国产成人鲁色资源国产91色综 | 欧美精品少妇一区二区三区| 日韩国产精品久久久久久亚洲| 一区二区三区在线视频免费观看| 中文天堂在线一区| 成人免费一区二区三区在线观看| 精品视频色一区| 欧美女孩性生活视频| 97国产一区二区| 欧美综合一区二区三区| 蜜臀精品一区二区三区在线观看| 午夜国产不卡在线观看视频| 日本不卡一二三区黄网| 国产一区 二区 三区一级| 一区二区三区不卡在线观看| 亚洲人成精品久久久久| 一区二区成人在线观看| 亚洲最大色网站| 欧美aaaaaa午夜精品| 国产精品一线二线三线| 成人一区在线看| 色综合 综合色| 91精品国产综合久久精品麻豆 | 成人aa视频在线观看| 一本久久a久久精品亚洲| 色哟哟一区二区在线观看| 制服丝袜av成人在线看| 精品国产麻豆免费人成网站| 欧美国产日韩精品免费观看| 7777精品伊人久久久大香线蕉| 欧美一卡二卡三卡| 国产午夜精品福利| 亚洲一区在线播放| 国产福利精品一区二区| 91精品国产综合久久久久久久久久| 国产亚洲美州欧州综合国 | 亚洲日本丝袜连裤袜办公室| 亚洲成人综合视频| 亚洲男人的天堂一区二区| 午夜视频一区在线观看| 国产精品88888| 欧美日韩国产三级| 中文字幕av资源一区| 日日欢夜夜爽一区| 91最新地址在线播放| 精品国产sm最大网站免费看| 亚洲欧美另类久久久精品| 久久精品99久久久| 激情文学综合插| 欧美在线观看你懂的| 国产三级精品视频| 久久精品人人做| 亚洲一区二区在线免费看| 国产伦精品一区二区三区免费| 欧美日韩一区三区| 中文字幕一区在线观看视频| 国内精品久久久久影院一蜜桃| 欧美伊人久久大香线蕉综合69| 中文字幕电影一区| 国产精品99久| 久久久亚洲精品一区二区三区 | 五月婷婷综合在线| 99国产精品视频免费观看| 2020日本不卡一区二区视频| 日韩中文字幕区一区有砖一区 | 日韩不卡免费视频| 欧美午夜寂寞影院| 夜夜亚洲天天久久| 色综合天天在线| 色就色 综合激情| 国产精品进线69影院| 国产91富婆露脸刺激对白| 精品国产a毛片| 国产成人在线视频网址| 久久精品视频一区| 波多野结衣在线一区| 99精品在线免费| 久久九九影视网| 国产成人免费视频| 国产精品视频一二三区| 成人av网站免费观看| 国产精品成人一区二区三区夜夜夜 | 亚洲电影在线播放| 精品一区二区三区在线视频| 欧美日韩成人高清| 日韩电影在线一区二区三区| 欧美精品 国产精品| 日本不卡一区二区三区高清视频| 欧美精品久久天天躁| 日本亚洲欧美天堂免费| 欧美不卡一区二区三区| 国产盗摄精品一区二区三区在线| 中文字幕乱码久久午夜不卡| 99麻豆久久久国产精品免费 | 亚洲成人免费电影| 日韩免费视频线观看| 成人免费视频一区二区| 亚洲一区二区三区在线播放| 91精品国产欧美日韩| 国产黄色精品网站| 亚洲综合激情网| 精品1区2区在线观看| 99精品视频在线观看| 日韩电影一区二区三区| 中文幕一区二区三区久久蜜桃| 欧美亚洲综合一区| 成人中文字幕合集| 青草av.久久免费一区| 国产精品乱码一区二区三区软件 | 波多野结衣中文字幕一区二区三区| 一区二区三区欧美激情| 精品国产电影一区二区| 欧美影视一区在线| 国产精品一区二区免费不卡| 亚洲午夜电影在线| 国产精品免费免费| 精品国产乱码久久久久久久久| 欧美亚洲动漫另类| 国产成人精品aa毛片| 亚洲国产成人porn| 精品一区二区三区视频 | 日韩美女精品在线| 精品国产sm最大网站免费看| 欧美午夜一区二区三区免费大片| 国产成人av电影| 免费成人在线视频观看| 亚洲一区二区三区在线播放| 中文字幕中文字幕在线一区| 欧美电影精品一区二区| 欧美日本在线播放| 91极品视觉盛宴| 国产成都精品91一区二区三| 免费成人在线网站| 蜜臀久久99精品久久久久宅男| 亚洲男人的天堂网| 中文字幕在线免费不卡| 欧美激情综合五月色丁香| 久久综合色一综合色88| 精品卡一卡二卡三卡四在线| 日韩视频免费观看高清在线视频| 欧美午夜电影网|