CouchDB - 从视图中“采集”最近邻文档。

时间:2013-09-18 10:22:17

标签: database oop mapreduce couchdb

不确定这个问题是怎么发出的,但我还是想把蝙蝠信号丢掉...... 我有一个类似于以下的数据集:

[
    { name: "Peter", score: 1000 },
    { name: "James", score: 800 },
    { name: "John", score: 600 },
    { name: "Saul", score: 400 },
    { name: "David", score: 200 }
]

现在我想对这个系列做一些事情,但我热衷的主要功能是获取一个给定的记录,找到直接位于上方和下方的文件。分数表中的项目,如;

[
    { name: "James", score: 800 },
    -> { name: "John", score: 600 },
    { name: "Saul", score: 400 }
]

我还想创建一个如下所示的视图:

[
    { key: 1, value: { name: "Peter", score: 1000 } },
    { key: 2, value: { name: "James", score: 800 } },
    { key: 3, value: { name: "John", score: 600 } },
    { key: 4, value: { name: "Saul", score: 400 } },
    { key: 5, value: { name: "David", score: 200 } }
]

我无法帮助,但我觉得这两个问题是相关的。 我也热衷于表演"采摘"在尽可能少的REST请求中......

我也很乐意接受依赖于应用层的解决方案,但同样,我希望避免多次访问数据库,并且还希望避免提取超出必要数据的数据。

有什么想法吗?

3 个答案:

答案 0 :(得分:1)

您可以创建一个以分数为键的视图。 map函数只需要emit(doc.score, null),其中doc是传递给函数的文档。如果您使用startkey=600limit=2descending=false查询此视图,您将获得分数为600和800的文档。如果您使用startkey=600查询,{{1 }和limit=2,您将获得分数为600和400的文档。

要按降序排列顺序获取所有文档,您只需使用descending = true查询,而不查询其他参数。您当然不会获得descending=true字段,但您可以轻松地在应用层中添加该字段。

答案 1 :(得分:1)

您是否尝试过将分数作为关键?在这种情况下,您可以构建评级图表并查询在某个范围内得分的人员。你的地图功能:

function(doc){
    emit(doc.score, {'name': doc.name, 'score': doc.score})
}

//不确定你是否还需要这样的值

现在,如果你打电话给你的观点,你会收到:

{
  "total_rows": 5, "offset": 0, "rows": [
    {"id": "1", "key": 200, "value": {"name": "David", "score": 200}},
    {"id": "2", "key": 400, "value": {"name": "Saul", "score": 400}},
    {"id": "3", "key": 600, "value": {"name": "John", "score": 600}},
    {"id": "4", "key": 800, "value": {"name": "James", "score": 800}},
    {"id": "5", "key": 1000, "value": {"name": "Peter", "score": 1000}}
  ]
}

看起来不像最高评级。我们添加descending=true查询参数:

{"total_rows": 5, "offset": 0, "rows": [
  {"id": "5", "key": 1000, "value": {"name": "Peter", "score": 1000}},
  {"id": "4", "key": 800, "value": {"name": "James", "score": 800}},
  {"id": "3", "key": 600, "value": {"name": "John", "score": 600}},
  {"id": "2", "key": 400, "value": {"name": "Saul", "score": 400}},
  {"id": "1", "key": 200, "value": {"name": "David", "score": 200}}
]}

好!现在,您可以应用startkey / endkey个查询参数来查询指定范围内的内容。我们来看startkey=799&endkey=401。请注意,边框值包含在响应中:

{"total_rows":5,"offset":2,"rows":[
  {"id":"3","key":600,"value":{"name":"John","score":600}}
]}

结果查询将显示为http://localhost:5984/db/_design/ddoc/_view/by_score?descending=true&startkey=799&endkey=401

答案 2 :(得分:-1)

我想我会创建一个数据集的轻量级视图(发出(“得分”,null),如Kxepal和Kim所建议的)拉出来,缓存它,并使用更改源保持新鲜。

这样,我最终会减少对数据库的攻击。这应该使得“采摘”过程更容易,因为我可以明确地向缓存的对象属性/元素添加“rank”属性,并使用它来挑选东西。

更新

虽然以上可以作为一个解决方案(Redis的一个可能的用例?),但使用视图响应total_rows和offset值会使得检索文档“rank”变得微不足道(基于“得分”视图,如以上两个答案)...

唯一仍然存在的问题是“pluck”本身,它可能仍然需要两个单独的API调用,但这可能不会那么糟糕......

仍然愿意接受建议。

干杯。 :)