索引键上的 cursor.skip() 总是更快吗?
Is cursor.skip() on indexed keys always faster?
我有2个数据库:slow
和fast
;每个数据库都有4096个条目。age
键是使用以下脚本生成的唯一随机整数:
var arr = []
while(arr.length < 4096){
var randmnum=Math.ceil(Math.random()*1000000)
var found=false;
for(var i=0;i<arr.length;i++){
if(arr[i]==randmnum){found=true;break}
}
if(!found)arr[arr.length]=randmnum;
}
var i=0;
for (i=0 ; i< arr.length; ++i) {
db.fast.insert({name:"john doe", email:"once@upon.a.time.com", age:arr[i]});
db.slow.insert({name:"john doe", email:"once@upon.a.time.com", age:arr[i]});
}
然后在蒙戈壳中:
> db.createCollection("slow")
> db.createCollection("fast")
> load("theAboveScript.js")
> db.fast.createIndex({"age":1})
如果我测试find
并sort
在fast
db 上完成的work
量低于预期的slow
。此外,索引/快速数据库的执行时间大约快 2 倍。
但是当我执行以下操作时:
> pageNumber=18;nPerPage=20; db.slow.find().skip(pageNumber > 0 ? ((pageNumber-1)*nPerPage) : 0).limit(nPerPage).explain("executionStats")
> pageNumber=18;nPerPage=20; db.fast.find().skip(pageNumber > 0 ? ((pageNumber-1)*nPerPage) : 0).limit(nPerPage).explain("executionStats")
工作量完全相同,执行时间也差不多,甚至快速数据库也慢了一点。
为什么 cursor.skip() 如果它适用于索引键,它不会得到任何提升?我希望分页返回排序的分页数据,而无需对其进行显式排序。
您的两个查询都没有对age
进行过滤,因此没有理由使用该索引。
如果您在 age
上添加条件,也会有所不同(即使文档如此之少,差异很小)
> pageNumber=18;nPerPage=20; db.slow.find({age:{$gt:200}}).
skip(pageNumber > 0 ? ((pageNumber-1)*nPerPage) : 0).limit(nPerPage).
explain("executionStats")
# "executionTimeMillis" : 14,
# "inputStage" : {
# "stage" : "COLLSCAN",
> pageNumber=18;nPerPage=20; db.fast.find({age:{$gt:200}}).
skip(pageNumber > 0 ? ((pageNumber-1)*nPerPage) : 0).limit(nPerPage).
explain("executionStats"
# "executionTimeMillis" : 0,
# "inputStage" : {
# "stage" : "IXSCAN",
如图所示,您在 AGE 字段上有索引,因此按索引字段搜索速度更快。
分页问题来自这样一个事实,即您的查询未被覆盖,这意味着它需要获取完整的文档 - 因此在这种情况下索引不会发挥作用。
请参阅此处以供参考
相关文章:
- 如何使用skip参数使用angular ui引导进行服务器端分页
- javascript检查值是否为mongo.cursor
- 为什么 cursor.skip() 如果所有键都已索引,有时会慢 3 倍
- 索引键上的 cursor.skip() 总是更快吗?
- Meteor cursor.fetch().property returns "undefined"
- MongoDB cursor.each 抛出错误
- 使用 BreezeJS 的 WebAPI 在我使用 $skip 时立即抛出错误
- query.skip() 不适用于推送安装
- :hover { cursor: 指针 } 在通过 borderradius 创建的圆上,即使在圆之外也会使其成为指针
- nodejs中的Mongodb Tailable Cursor,如何停止流
- cursor.find()回调未在metrojs中返回
- 什么是minimongo(流星)限制?cursor.toArray()使客户端失败
- MongoDB Cursor没有方法'next'
- this.style.cursor='手',当我把鼠标悬停在元素上时,第一次没有工作
- 我应该如何在javascript中声明for cursor变量
- Contenteditable <div>: Cursor starts before the placeh
- 移除选中的(高亮显示的)元素,除了输入#cursor
- 为什么他们使用保留关键字'continue'在IndexedDB's Cursor对象中命名一个
- cursor.toArray()返回promise而不是array
- 如何在一个查询中使用.skip()、.limit()和全部匹配结果进行MongoDB文本搜索