我有一个存储过程,我在其中创建一个临时表,通常包含1到10行。在存储过程中,此表被截断并填充多次。它被截断,因为这比删除更快。 当我因使用删除而遭受惩罚(截断对表变量无效)时,我是否通过用表变量替换此临时表来获得性能提升
虽然表变量主要在内存中,并且通常比临时表更快,但我是否通过删除而不是截断来消除任何好处?
答案 0 :(得分:11)
将以下内容运行到脚本中,似乎表变量是更好的选择
CREATE TABLE #Temp(
ID INT
)
DECLARE @Int INT,
@InnerInt INT
SELECT @Int = 1,
@InnerInt = 1
WHILE @Int < 50000
BEGIN
WHILE @InnerInt < 10
BEGIN
INSERT INTO #Temp SELECT @InnerInt
SET @InnerInt = @InnerInt + 1
END
SELECT @Int = @Int + 1,
@InnerInt = 1
TRUNCATE TABLE #Temp
END
DROP TABLE #TEMP
GO
DECLARE @Temp TABLE(
ID INT
)
DECLARE @Int INT,
@InnerInt INT
SELECT @Int = 1,
@InnerInt = 1
WHILE @Int < 50000
BEGIN
WHILE @InnerInt < 10
BEGIN
INSERT INTO @Temp SELECT @InnerInt
SET @InnerInt = @InnerInt + 1
END
SELECT @Int = @Int + 1,
@InnerInt = 1
DELETE FROM @Temp
END
来自Sql Profiler
CPU Reads Writes Duration
36375 2799937 0 39319
vs
CPU Reads Writes Duration
14750 1700031 2 17376
答案 1 :(得分:7)
坦率地说,只有10或20(甚至100)个条目,速度的任何差异都将在亚纳秒范围内。忘掉它 - 甚至不要浪费你的大脑时间 - 这不是问题!
一般
表变量将保留在内存中一定的大小 - 如果它们超出了这个范围,它们也会被转换到tempdb
数据库中的磁盘 - 就像临时表一样。另外:如果一个临时表只有少数几个条目,那么它们最像是存储在一个8k页面上,一旦你访问其中一个条目,整个页面(以及整个临时表)就会在SQL Server内存中 - 所以即使在这里,表变量也没有很多好处......
表变量不支持索引或统计信息,这意味着如果您有多个条目,特别是如果您需要搜索和查询此“实体”,那么您最好暂时使用表
总而言之:我个人比表变量更经常使用临时表,特别是如果我有超过10个条目或类似的东西。能够对临时表进行索引并对其进行统计,与表变量可能具有的任何潜在收益相比,通常可以获得大量的时间。