ruby-on-rails - Ruby 部分检索大量记录并迭代它们

标签 ruby-on-rails ruby collections iterator persistent-storage

我是 Ruby 的新手,但我在其他编程语言方面有很多经验。我需要遍历大量记录(来自数据库或任何持久存储)。存储引擎允许我按范围部分检索记录。在 PHP 中,我通常编写自定义迭代器来加载记录范围,并在需要时加载记录的下一部分而忘记前一部分。脚本内存使用和存储请求计数之间的一些权衡。像这样的东西(从评论 here 复制):

class Database_Result_Iterator {
...
private $_db_resource = null;
private $_loaded = false;
private $_valid = false;

function rewind() {
    if ($this->_db_resource) {
        mysql_free($this->_db_resource);
        $this->_db_resource = null;
    }
    $this->_loaded = false;
    $this->_valid = false;
}

function valid() {
    if ($this->_loaded) {
        $this->load();
    }
    return $this->_valid;
}

private function load() {
    $this->_db_resource = mysql_query(...);
    $this->_loaded = true;
    $this->next(); // Sets _valid
}

这种方法在 Ruby 中是如何转换的? IE。我有一些类 Voter 和方法 get_votes 返回所有 votes 属于当前选民对象。可以检索的不是包含所有选票的数组,而是可以对其进行迭代的选票集合。我该如何实现?

更新

请不要将 ActiveRecord 和 RDBMS 仅视为一种可能的存储方式。那么 Redis 作为存储和 LRANGE 之类的命令呢?我对在 Ruby 中解决这类问题的通用代码模式很感兴趣。

最佳答案

来自guides在 Ruby on Rails 上:

User.all.each do |user|
  NewsLetter.weekly_deliver(user)
end

效率很低。首先,您可能希望在数据库中进行大部分过滤。为此,ActiveRecord 提供了一个名为 find_each 的方法:

User.find_each(:batch_size => 5000) do |user|
  NewsLetter.weekly_deliver(user)
end

:batch_size 参数允许获取数据片段而不是获取整个结果集。在大多数情况下非常有帮助。

但是,您可能一开始就不想对所有记录进行操作:

User.with_newsletter.each do |user| 
   NewsLetter.weekly_deliver(user)
end

其中 with_newsletter 是所谓的 scope .

关于ruby-on-rails - Ruby 部分检索大量记录并迭代它们,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/16497062/

相关文章:

ruby-on-rails - ActionDispatch::Routing::RouteSet#call Rails 4.1 真的很慢

生产环境中缺少 javascript_include_tag 文件 ( 404 )

ruby-on-rails - rails : Undefined method `truncate' in model

asp.net-mvc - ASP.NET MVC 编辑集合最佳实践 - 您的意见

wpf - 如何在 M-V-VM 设计模式中最好地表示集合中的可选项目?

ruby-on-rails - 用于查找丢失的外键的 Rails 插件

ruby-on-rails - omn​​iauth 和电子邮件密码注册的最佳做法是什么?

ruby - 如何在 Windows 上安装 ruby​​ 2.1.2?

c - 为什么此代码不适用于 ruby​​ 1.9 但适用于 ruby​​ 1.8?

java - 如何使用另一个列表中的对象的属性创建一个新列表