Sql server 为什么可序列化隔离级别会导致死锁和并发问题?

Sql server 为什么可序列化隔离级别会导致死锁和并发问题?,sql-server,concurrency,isolation-level,database-deadlocks,Sql Server,Concurrency,Isolation Level,Database Deadlocks,我知道这样一种理论,即在事务的持续时间内,在可序列化的隔离级别中,使用范围锁和写锁进行读取。我可以理解有人这样说:“在所有条件相同的情况下,可序列化隔离可能(但不一定)导致比任何其他隔离级别更低的并发性”。但按照所有博客/文档所述,较低的并发性和较高的死锁似乎是必然的。我正在试图理解为什么在我的特殊情况下,从实际意义上讲应该如此。以下是我的问题 如果不同的连接没有访问同一组记录,那么可序列化的隔离级别是否会导致并发性降低?我假设是一个经过“微调”的OLTP系统,其中每个查询都是一个“点查询”,只

我知道这样一种理论,即在事务的持续时间内,在可序列化的隔离级别中,使用范围锁和写锁进行读取。我可以理解有人这样说:“在所有条件相同的情况下,可序列化隔离可能(但不一定)导致比任何其他隔离级别更低的并发性”。但按照所有博客/文档所述,较低的并发性和较高的死锁似乎是必然的。我正在试图理解为什么在我的特殊情况下,从实际意义上讲应该如此。以下是我的问题

  • 如果不同的连接没有访问同一组记录,那么可序列化的隔离级别是否会导致并发性降低?我假设是一个经过“微调”的OLTP系统,其中每个查询都是一个“点查询”,只返回几行,优化器会提出很好的计划。我也在考虑数据页,而不是索引页

  • 为什么僵局会增加?这些是由于索引页的更新造成的吗?但这些可能发生在任何隔离级别,而不是快照隔离。那么为什么要选择可序列化隔离级别呢


  • 我当然会接受这样的答案,即‘根据用户输入,你永远不知道你的执行计划何时会出问题。’。通过设置高于要求的隔离级别,您正在使糟糕的情况变得更糟。因此,设置最适合您的最高隔离级别。

    简单的回答是,从
    读取未提交的
    一直到
    可序列化的
    ,您最终会取出更多不同类型的锁。在某种程度上,它是有意义的;除此之外,数据库引擎如何能够做出以下保证

    在当前事务完成之前,其他事务无法插入键值在当前事务中任何语句读取的键值范围内的新行

    进一步在文档中,它直截了当地说,范围锁被取出。因此,如果您执行类似于从dbo.yourTable中选择*的操作,其中ID介于1和50之间,并且当前表中只有10行(比如ID 1-10),那么您的应用程序将无法:

    • 插入IDs 11-50的任何数据
    • 删除/更新1-10中的任何一项

    如果你需要它,你就需要它。但要知道你在干什么;放置的共享范围锁与许多内容不兼容(读取“将导致阻塞”)。有关详细信息,请参阅。

    如果连接采用范围锁定,我当然同意您的看法。但是,如果两个不同的用户连接很少访问完全相同的记录/页面,您的答案是否仍然有效?使用范围锁,您锁定了一个元结构。也就是说,对于试图将其修改为阻止的操作,数据甚至不需要存在(请参见上面的要点)。因此,如果您知道您的两个(或更多)应用程序将修改不相交的范围,那么您就可以了。但我要反驳的是:那时候为什么需要序列化隔离呢?谢谢Ben。关于“那时候为什么需要序列化隔离?”,我们还没有做出决定。我们正在了解每个隔离级别的特点、优点和缺点,并将其应用于我们的情况。你的回答很有帮助。我将试着把你的回答作为一个答案。上一次我尝试的时候,网站没有让我说“我需要x点才能这么做”。