2

不知道这个问题听起来如何,但我想无论如何我都会抛出 Bat 信号......我有一个类似于以下的数据集:

[
    { 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 请求中执行“采摘”......

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

有任何想法吗?

4

3 回答 3

1

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

要按分数降序获取所有文档,您只需使用 descending=true 进行查询,无需其他参数。你当然不会得到一个key: n字段,但是你可以很容易地在你的应用层中添加它。

于 2013-09-18T10:54:55.357 回答
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

于 2013-09-18T11:00:08.510 回答
-1

我想我将创建数据集的轻量级视图(emit("score", null),正如 Kxepal 和 Kim 所建议的那样)将其拉出、缓存并使用更改提要使其保持新鲜。

这样,我最终会减少访问数据库的次数。这应该使“采摘”过程在某种程度上更容易,因为我可以明确地将“等级”属性添加到缓存的对象属性/元素中,并使用它来挑选东西。

更新:

尽管以上可以作为解决方案(Redis 的一个可能用例?),但使用视图响应 total_rows 和偏移值使得检索文档“排名”变得微不足道(基于“分数”视图,如上面两个答案中所建议的那样)...

唯一仍然存在的问题是“采摘”本身,它可能仍然需要两个单独的 API 调用,但这可能还不错……

不过仍然对建议持开放态度。

干杯。:)

于 2013-09-18T11:57:35.320 回答