2009-10-23 131 views
7

这对于数以百万计的记录速度是:永久表临时表?表VS临时表的性能

我只能使用它为1500万条记录。处理完成后,我们删除这些记录。

+2

这很大程度上取决于情况。你想用它做什么? – 2009-10-23 18:49:21

+0

Permannent表。您连接到服务器,百万条记录已经存在,无需任何操作,亚纳秒时间! ......也许你很想详细说明你的问题? – 2009-10-23 18:53:53

+0

我必须处理5000万条记录。为此我必须创建永久/临时表。 情景是:对于处理5000万条记录,我创建了另一个?/?表并插入到此表中。然后我应用优先级为(Fname)并将其插入到另一个永久\临时表中并从第一个表中删除。并应用优先级2,然后再重新执行第一步。所以我问了这个问题。请回复。 – ManishKumar1980 2009-10-23 19:04:22

回答

14

在你的情况,我们使用一个永久表称为临时表。这是大量进口的常用方法。实际上,我们通常使用两个临时表,一个包含原始数据,另一个包含清理后的数据,这使得用Feed更容易研究问题(它们几乎总是由我们的客户发送给我们的新的多种方式产生的,我们必须能够证明这一点)。另外,您避免像有成长临时数据库或导致问题谁想要使用的临时数据库,但必须等待它成长为你的其他用户等问题

您还可以使用SSIS并跳过临时表(S ),但我发现无需重新加载50,000,000张桌子就可以返回并进行研究,这非常有帮助。

+0

SSIS可能是最好的解决方案 – 2009-10-23 19:39:01

+2

+1指出了额外的好处在发生错误时可以看到分阶段的数据 - “您也可以使用SSIS并跳过登台表,但我觉得无需重新加载50,000,000个表格就可以返回并进行研究,这非常有帮助。” – Mayo 2009-10-23 19:40:43

2

永久表是更快,如果表结构是100%相同的,因为没有开销分配空间和建表。

临时表是在某些情况下更快(例如,当你不需要的索引是存在于永久表,这将减缓插入/更新)

-1

临时表是在内存中(除非他们太大),所以理论上它们应该非常快。 但通常不会。 作为一个经验法则,尽量远离临时表,除非这是唯一的解决方案。 你能给我们提供一些关于你想要做什么的更多信息吗?这也许可以用一个派生查询

+7

Temp变量存储在Memory not Temp表中。 – ManishKumar1980 2009-10-23 18:57:00

+1

我没有看到问题是MSSQL。在MySQL中,您可以声明一个临时内存表:'CREATE TEMPORARY TABLE test ENGINE = MEMORY' – adamJLev 2009-10-23 21:53:53

+1

表变量显然也存储在tempdb中 - 请参阅http://dba.stackexchange.com/questions/16385/whats-the-difference- 16386#16386 – flash 2014-03-14 15:36:40

0

我个人会使用一个永久性表并在每次使用前截断它。根据我的经验,它更容易理解/维护。然而,我最好的建议是尝试两种方法,看看哪一种效果更好。

+2

只有当这个进程是一个singleton,并且没有任何其他进程在此期间启动并且还需要使用该表的情况下,这才会起作用。 我们有导入大量数据的进程,因为多个进程可能同时运行,所以我们无法截断单个表。 – 2009-10-24 14:26:53

+0

您可以通过使用具有唯一列的perm表来标识导入过程,该过程使用特定的一组数据。我们有这些用于用户驱动的基于文件的导入(而不是截断工作正常的夜间批处理)。可能考虑一个清理过程来检查桌子的大小。 – Mayo 2009-10-25 13:05:52

11

如果不使用tempdb,请确保您的工作在数据库的恢复模式未设置为“全”。这会在这些50M行插入上造成很多开销。

理想情况下,你应该使用一个临时数据库,简单恢复模式,在RAID 10,如果可能的话,并调整其大小提前为所有您的操作提供足够的空间。关闭自动增长。

使用INSERT ... WITH(TABLOCK),以避免行级日志记录:

INSERT INTO StagingTable WITH (TABLOCK) (.....) 
SELECT ..... 

同样的BULK INSERT。如果删除并重新创建,请先创建您的聚簇索引,然后再插入。如果不能,首先插入一个表中,然后将其插入到具有正确群集的另一个表中,然后截断第一个表。如果可能的话,避免在BULK INSERT上使用小批量。请仔细阅读BULK INSERT文档,因为您可以通过错误的选项来破坏性能。

避免INSERT ... EXEC。每一行都被记录下来。

避免更新,除非你需要计算运行总和。通常,从一个表插入另一个表比较便宜,然后截断第一个表,而不是更新到位。运行总计算是例外,因为它们可以通过UPDATE和变量在行之间累积值来完成。

避免表控制结构以外的表变量,因为它们阻止并行化。不要将您的50M行表连接到表变量,而是使用临时表。

不要害怕迭代的游标。使用游标变量,并使用STATIC关键字针对聚集索引前面的低基数列声明它们。用这个将大表分成更易于管理的块。

不要试图在任何一个陈述中做太多。

+0

非常不错和Satisfoctory答案。感谢所有人 – ManishKumar1980 2009-10-24 07:40:57