【问题标题】:How to disable locking on the table in SQL Server?如何在 SQL Server 中禁用对表的锁定?
【发布时间】:2015-09-10 18:21:58
【问题描述】:

我需要存储数据,在大多数情况下,数据的生命周期应该是 1-30 分钟(但仍然可以是 1 天/1 周)。这只是一个特定的项目 - 许多用户执行的大量批量操作。

因此,处理这些数据的典型过程:

  1. 用户上传一个文档,我们解析它并将数据推送到表中(插入 100-70000 行)
  2. 我们验证数据并向用户显示错误
  3. 用户更正数据(单次更正 - 更新 1 行)
  4. 用户运行一个操作,之后从表格中删除所有从文档上传的数据。

当只有单个用户使用系统时,这很有效。当许多用户上传产生大约 1-5 千行的文档时,这很有效。 但是在插入 10000 行之后,SQL Server 会强制锁定表并且......这是一个问题。

所以,有不同的方法可以解决这个问题,但它们都很丑:

  1. 切换到键值存储 - 客户不同意使用其他存储
  2. 由于多种原因无法切换到内存解决方案
  3. 将插入分组到 2000 行并为每个行指定不同的事务 & 手动处理失败 - 太丑了

接下来我要:关闭指定表上的任何锁定。不需要一致性,只有索引才能工作。

我怎样才能做到这一点?任何其他想法也受到赞赏。

【问题讨论】:

  • 如果不知道是什么导致锁定,很难说解决您的表锁定问题的最佳解决方案是什么。您如何将数据加载到表中?是在表格上锁定的验证/更正吗?如果是这样,您可能需要考虑使用第二个临时表将数据加载到其中以执行验证步骤,然后再将其合并到实时表中。
  • 当你插入 10-20000 行时,锁升级仍然会发生。这是一个需要表锁的大规模插入,因为要在单个语句中插入这么多数据,需要做很多事情。您是否考虑过使用 BULK INSERT?或者批量插入。
  • @nsinreal 是 tablelock 阻塞了其他查询什么的。如果是这样,您也许可以将隔离级别更改为 Read Commited Snapshot.
  • 在单个插入/批处理中插入 10-2 万行时,无法避免锁升级。如果您想避免使用那么多行的表锁升级,您将不得不分批执行此操作。这意味着这里需要一些循环。
  • 您支持多少并发用户?是否有可能将流量分成每个用户一张表?您可以根据需要创建和删除表,或者在回收时保留一个表池和TRUNCATE

标签: sql sql-server tsql transactions locking


【解决方案1】:

您可以通过 ALTER TABLE mytable SET(LOCK_ESCALATION=DISABLE) 在表级别禁用锁升级。有关详细信息,请参阅https://msdn.microsoft.com/en-us/library/ms190273.aspx

重要提示:锁升级是一种基本的资源治理方法。禁用它会导致显着更高的内存消耗,这反过来又会对下游产生各种影响,因此在松开之前彻底测试。这是 32 位平台的一个主要问题,它将任何应用程序的 VAS 限制为 4GB,无论服务器上安装了多少 RAM。上面的任何东西都只能用于数据缓存。借助 64 位平台,SQL Server 能够将您板载的任何内存用于任何目的。

【讨论】:

    猜你喜欢
    • 2019-07-29
    • 2016-01-04
    • 2023-04-03
    • 1970-01-01
    • 1970-01-01
    • 2022-01-11
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多