2015-02-09 54 views
0

为了下面的例子我写了用户,俱乐部和追随者集合。 我想从“用户”集合中找到“A famous club”之后的所有用户文档。 我如何找到这些?哪种方式最快?关于 'what do I want to do - Edge collections'查询MongoDB(使用边缘集合 - 最有效的方法?)

更多信息

用户收集

{ 
    "_id": "1", 
    "fullname": "Jared", 
    "country": "USA" 
} 

俱乐部收集

{ 
    "_id": "12", 
    "name": "A famous club" 
} 

关注集合

{ 
    "_id": "159", 
    "user_id": "1", 
    "club_id": "12" 
} 

PS:我可以像下面的方式使用Mongoose来获取文档。但是,创建followers阵列需要约8秒150.000条记录。第二个find查询 - 使用追随者数组查询 - 需要大约40秒。这是正常的吗?

Clubs.find(
    { club_id: "12" }, 
    '-_id user_id',  // select only one field to better perf. 
    function(err, docs){ 

     var followers = []; 
     docs.forEach(function(item){ 
      followers.push(item.user_id) 
     })     

     Users.find(
      { _id:{ $in: followers } }, 
      function(error, users) { 
       console.log(users) // RESULTS 
     }) 
}) 
+0

我没有看到这个问题......你问:“我怎么能找到它”,但你自己提供的解决方案。你的目标是什么?为什么你甚至需要*一个特定俱乐部的所有追随者的所有数据?显示这些结果可能没有意义?!没有更多的上下文,没有什么可以添加到您的问题... – mnemosyn 2015-02-09 17:06:13

+0

你好@mnemosyn,你是对的。我编辑了这个问题。我需要最有效的方法。如果在数百万条记录上工作。感谢您的关注。 – efkan 2015-02-09 17:27:38

+0

为什么你一次只需要RAM中的所有数据?无论如何,你必须找出延迟来自哪里。请记住,默认批量大小仅为1,000,因此此代码至少需要450次数据库往返行程,以及实际的数据传输。我不知道猫鼬的开销是多少,但分析它可能会有所帮助。另外,数组大于10,000个元素的'$ in'可能会很慢。如果您几乎需要所有数据,那么将所有数据首先加载到RAM中可能会更快吗?或者整个数据集大得多? – mnemosyn 2015-02-09 18:39:57

回答

0

在MongoDB上没有一个符合条件的公式来操纵连接多对多关系。所以我把集合作为下面的嵌入式文档。但在这种情况下最重要的是创建索引。例如,如果您想通过followingClubs进行查询,您应该使用Mongoose创建一个像schema.index({ 'followingClubs._id':1 })的索引。如果你想查询countryfollowingClubs你应该像schema.index({ 'country':1, 'followingClubs._id':1 })

注重与嵌入式文档时创建另一个指标:http://askasya.com/post/largeembeddedarrays

然后你就可以得到您的文档快速度。我试图用这种方式获得150.000条记录,只花了1秒钟。这对我来说已经足够了...

ps:我们忘不掉在我的测试中我的Users集合从未经历过任何数据碎片。因此我的查询可能会表现出色。特别是followingClubs嵌入式文件的数组。

用户收集

{ 
    "_id": "1", 
    "fullname": "Jared", 
    "country": "USA", 
    "followingClubs": [ {"_id": "12"} ] 
} 

俱乐部收集

{ 
    "_id": "12", 
    "name": "A famous club" 
}