2

由于某些原因,我需要在我的 couchdb 中获取每 50 个文档。

例如,我的数据库中有 500 个用户,我想获取第一个、第 51 个、第 101 个......第 451 个用户。

如何通过 map/reduce 函数得到这个结果?

(我知道我可以在 url 中设置“skip”参数来执行类似的行为,但我想通过 map/reduce 来实现)

谢谢!

4

1 回答 1

3

问题

要记住的关键是 CouchDB map/reduce 更像CREATE INDEX...,而不像SELECT * FROM...

Map/reduce 创建一个静态的行列表。行可以按您想要的任何顺序排列(按您发出的排序),但一个文档不可能更改另一个文档的结果。

为了说明这一点,假设您有一个这样的行的假设视图。键是他们在列表中的“位置”,值是用户名

// View rows (conceptual diagram only)
// Key, Value
0     , "mark" // Suppose Alice was created first, 1 week ago
1     , "bob"  // and Bob was created 1 day ago
2     , "evan" // and Evan was created 1 hour ago... so this view is chronological
... // etc.

现在您意识到 Bob 的文档有错误。他实际上在一年前签约,而不是一天前。你更新他的时间戳。视图现在应该如何?

// View rows (conceptual diagram only)
// Key, Value
0     , "bob"  // The corrected Bob document was created 1 **year** ago
1     , "mark" // ...and now Mark scoots down to the next position (!!!)
2     , "evan" // ...and Evan stayed the same
... // etc.

问题来了:在 CouchDB 中,如果只更改 Bob 的文档,是不可能影响 Mark 的行的。这就是基本架构。上面的(!!!)标签表示不可能的功能。问题是我们最初的假设:我们可以有一个视图来指示行对于彼此的绝对位置。(注意,relative 一词与relative具有相同的词根,如“关系数据库”)

因此,通过减少荒谬,这种技术是不可能的。

解决方案

你可以用 map/reduce 做大部分你需要的事情。代替假设的位置作为键,使用时间戳作为键。

// View rows (conceptual diagram only)
// Key, Value
2011-05-06, "bob"  // Bob signed up one year ago
2012-05-05, "mark" // Mark signed up one day ago
2012-05-06, "evan" // Evan one hour ago
... // etc.

当然,时间戳格式只是为了做一个清楚的例子。您可能应该使用 ISO 8601 格式(即您从JSON.stringify(new Date)JavaScript 中获得的格式)。

要获得最新的注册,请对视图进行降序查询;并且要仅获得一行,请使用该limit选项。

  • 要获得最新的注册:?descending=true&limit=1
  • 要获得第 50 个最新的:?descending=true&limit=1&skip=50
  • 要获得第 100 个最新的:?descending=true&limit=1&skip=100
于 2012-05-06T00:38:21.290 回答