Warning: file_get_contents(/data/phpspider/zhask/data//catemap/6/mongodb/11.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
Mongodb mongo以单递增顺序保存文档_Mongodb - Fatal编程技术网

Mongodb mongo以单递增顺序保存文档

Mongodb mongo以单递增顺序保存文档,mongodb,Mongodb,我知道mongo文档提供了一种模拟自动增量的方法。 但它并不像MySQL所保证的那样具有并发性 考虑事件的顺序: 客户端1获得的索引为1 客户端2获得的索引为2 客户端2保存id为2的文档 客户端1保存id为1的文档 在这种情况下,可以保存id小于当前已保存最大值的文档。对于MySql,这永远不会发生,因为自动增量id是由服务器分配的 我如何防止这种情况?一种方法是在每个客户机上执行乐观循环,但对于许多客户机来说,这将导致严重的争用。还有更好的办法吗 这样做的用例是确保id只向前。这对于一个聊

我知道mongo文档提供了一种模拟自动增量的方法。

但它并不像MySQL所保证的那样具有并发性

考虑事件的顺序:

客户端1获得的索引为1 客户端2获得的索引为2 客户端2保存id为2的文档 客户端1保存id为1的文档 在这种情况下,可以保存id小于当前已保存最大值的文档。对于MySql,这永远不会发生,因为自动增量id是由服务器分配的

我如何防止这种情况?一种方法是在每个客户机上执行乐观循环,但对于许多客户机来说,这将导致严重的争用。还有更好的办法吗

这样做的用例是确保id只向前。这对于一个聊天室来说是很重要的,在聊天室中有许多信息被发布,并且信息被分页,我不希望在上一页中插入新的信息

但它并不像MySQL所保证的那样具有并发性

这取决于并发证明的定义,但让我们看看

在这种情况下,可以保存id小于当前已保存最大值的文档

这是正确的,但这取决于同时性和单调性的定义。假设您的代码快照了系统其他部分的状态,然后获取单调键,然后执行可能需要一段时间的插入。在这种情况下,这个显然非单调的插入实际上可能是“更单调的”,因为索引2确实是在稍后捕获的,可能反映了一种更为近期的状态。换句话说:插入的时间真的重要吗

对于MySql,这永远不会发生,因为自动增量id是由服务器分配的

那个。大多数关系数据库提供对这些特性的细粒度控制,因为严格的保证会严重影响并发性

MySQL既不能保证没有间隙,也不能保证在提交获得较低自动增量值的事务之前,具有较高自动增量id的事务对其他读卡器不可见,除非您保持表级锁,这会严重影响并发性

为GAPLESIONS,考虑两个并发插入的第一个事务回滚。第二次插入是否在提交时分配了新id?否-来自:

如果使用计数器回滚已生成数字的事务,则可能会看到分配给“自动增量”列的值序列中存在间隙。参见14.6.5.5.1的末尾,传统InnoDB自动增量锁定

在所有锁定模式0、1和2中,如果生成自动增量值的事务回滚,则这些自动增量值将“丢失”

此外,您完全忽略了复制的问题,在复制过程中,序列会导致更多的问题:

因此,保留到语句结束的表级锁使使用自动增量的INSERT语句可以安全地用于基于语句的复制。但是,当多个事务同时执行insert语句时,这些锁限制了并发性和可伸缩性。参见14.6.5.5.2可配置InnoDB自动增量锁定


InnoDB行为文档的篇幅足以提醒我们,在并发系统中做出明显简单的保证是多么复杂。是的,对于表级锁,插入的单调性是可能的,但很难令人满意。如果您对系统采取分布式视图,情况会变得更糟,因为我们甚至无法确定分区模式下的计数器值…

嗯,原子操作的$incis。就我所阅读的文档和我所知,只要你创建一个唯一的索引或不使用upserts,使用序列是坚如磐石的。评论就是评论。B这是生成序列的快捷方式。序列本身是单调递增的。这就是原子的固有含义。唯一不能保证的是先到先得,因为没有锁。但是,只要满足上述要求,每个请求将获得一个唯一的序列号。c既然你想穿smarty pant:Da代码,请!我明白这一点,我两个都回答了。只有在使用表级锁时,才会出现仅向前的行为,这严重限制了并发性您想要的听起来更像实时消息队列请参见MongoDB中的可定制游标,而不是单调字段。对于一个单调的字段,时间戳就可以了,但是如果你担心客户端速度慢,那么时钟同步问题就不那么重要了,例如毫秒级的事情,请参阅Lamport在'78年的论文。对于简单的分页,使用基于时间戳的方法,并假设人们不会以不合理的频率发布,例如在MongoDB中使用ObjectId