`
jbf034
  • 浏览: 152328 次
  • 性别: Icon_minigender_1
  • 来自: 杭州
社区版块
存档分类
最新评论

acts as list/acts as tree

阅读更多
Acts As List

在子表中使用acts_as_list,便能从父表的“视图”中得到像子表的行为。父表将能够
遍历子表,在列表内移动子表,或从列表内移除子表。
通过给每个子表一个位置数来实现列表。这意味着子表必须有个列来记录此位置。如果
我们称它为列position,Rails 会自动使用它。如果不这么称呼它,我们需要告诉Rails 它
的名字。对于我们的例子,跟随父表之后我们将创建一个新的子表(叫children)。
create table parents (
id int not null auto_increment,
primary key (id)
);
create table children (
id int not null auto_increment,
parent_id int not null,
name varchar(20),
position int,
constraint fk_parent foreign key (parent_id) references parents(id),
primary key (id)
);
接着,我们将创建“模型”类。注意在Parent 类中,我们基于当前的position 列的值
来确定我们children 的位置。这确保从数据库内获得的数组在正确的定单清单内。
class Parent < ActiveRecord::Base
has_many :children,rder => :position
end
class Child < ActiveRecord::Base
belongs_to :parent
acts_as_list :scope => :parent_id
end
在Child 类中,我们用传统的belongs_to 声明来建立与父表的连接。我们也有个
acts_as_list 声明。我们用一个:scope 选项来限制它,指定列表的每个父表。没有这范围操
作符,则对于children 表内的所有条目则只有一个全局的列表。
现在我们设一些测试用数据:我们为一个特定的父项创建四个子项,称为One,Two,Three
和Four。
parent = Parent.new
%w{ One Two Three Four}.each do |name|
parent.children.create(:name => name)
end
parent.save
我们要写个简单的方法来检查列表的内容。
def display_children(parent)
puts parent.children.map {|child| child.name }.join(", ")
end
在完成我们列表的测试后。注释显示了由display_children()产生的输出。
display_children(parent) #=> One, Two, Three, Four
puts parent.children[0].first? #=> true
two = parent.children[1]
puts two.lower_item.name #=> Three
puts two.higher_item.name #=> One
parent.children[0].move_lower
parent.reload
display_children(parent) #=> Two, One, Three, Four
parent.children[2].move_to_top
parent.reload
display_children(parent) #=> Three, Two, One, Four
parent.children[2].destroy
parent.reload
display_children(parent) #=> Three, Two, Four
注意我们是如何在父项中调用reload()的。各种move_method 更新数据库内子项,但因
为它们直接操作子项,父项将不会立即知道这一更改。
list 库使用术语lower 和higher 来引用元素的相对位置。Higher 意味着离列表前部近,
lower 离尾部近。顶部也与前部是一个意思,底部与尾部是一个意思。方法move_higher( ),
move_lower( ), move_to_bottom( ), 和move_to_top( ) 在list 内循环移动一个特定项
目,并自动调整与其它元素的位置。
higher_item( ) 和lower_item( ) 返回相对于当前元素的下一个和前一个元素的位
置, first?( ) 和last?( ) 在list 内的当前元素位于前部或尾部时返回true 。
新近创建的子项被自动地添加到列表的尾部。当一个子行被删除时,list 内的子项会被
移除并用gap 填充。


Acts As Tree

“活动记录”提供对组织一个表内的行到一个层次,或树,结构中的支持。这对创建具
有子项的项目很有用处,并且这些子项还可以有它自己的子项。分类目录列表通常有这种结
构,如对许可证,目录清单等等的描述。
这种类似树的结构可通过向表中添加一个单独的列(缺省称为parent_id)来做到。这个
列是个引用自身表的外键,链接子行到它们的父行。图15.1 演示了它。
要显示出树是如何工作的,让我们创建个简单的分类表,每个顶层分类有子分类,每个
子分类可以添加子分类层。注意外键指回到自身表中。
create table categories (
id int not null auto_increment,
name varchar(100) not null,
parent_id int,
constraint fk_category foreign key (parent_id) references
categories(id),
primary key (id)
);
相应的“模型”使用带有种类名字acts_as_tree 的方法来指出这种关系。:order 参数
意味着当我们查找特定节点的子项时,我们会看到它们按它们名字列被重新排列。
class Category < ActiveRecord::Base
acts_as_treerder => "name"
end
通常你得有一些最终用户功能来创建和管理分类层次。这儿,我们只使用创建它的代码。
注意我们如何使用子项属性来管理任何节点的子项。
root = Category.create(:name => "Books")
fiction = root.children.create(:name => "Fiction")
non_fiction = root.children.create(:name => "Non Fiction")
non_fiction.children.create(:name => "Computers")
non_fiction.children.create(:name => "Science")
non_fiction.children.create(:name => "Art History")
fiction.children.create(:name => "Mystery")
fiction.children.create(:name => "Romance")
fiction.children.create(:name => "Science Fiction")
现在我们做好了所准备工作,我们可以试用树结构了。我们使用我们用于list 代码的
display_children()方法。
display_children(root) # Fiction, Non Fiction
sub_category = root.children.first
puts sub_category.children.size #=> 3
display_children(sub_category) #=> Mystery, Romance, Science Fiction
non_fiction = root.children.find(:first, :conditions => "name = 'Non
Fiction'")
display_children(non_fiction) #=> Art History, Computers, Science
puts non_fiction.parent.name #=> Books
我们用于操纵子项的各种方法看起来很熟悉:它们与提供给has_many 的是一样的。事实
上,如果我们看看acts_as_tree 的实现,我们将看到这做的所有事情都是构建在belongs_to
和has_many 属性上,每个都指回自身表。就像我们写的一样。
class Category < ActiveRecord::Base
belongs_to :parent,
:class_name => "Category"
has_many :children,
:class_name => "Category",
:foreign_key => "parent_id",
:order => "name",
:dependent => true
end
如果你需要优化子项大小的性能,你可以构建一个counter 缓存(就好像你在用
has_many)。添加选项:counter_cache => true 给acts_as_tree 声明,添加列
children_count 给你的表。
分享到:
评论

相关推荐

    acts_as_list.rar

    acts_as_list.raracts_as_list.raracts_as_list.raracts_as_list.raracts_as_list.raracts_as_list.raracts_as_list.raracts_as_list.raracts_as_list.raracts_as_list.raracts_as_list.raracts_as_list.raracts_as_...

    acts_as_authenticated

    2. **配置**:在`config/initializers/acts_as_authenticated.rb`中,你可以设置一些选项,如密码最小长度、哈希算法等。 3. **迁移**:acts_as_authenticated可能需要创建或修改数据库表,你需要运行相应的数据库...

    acts_as_list, 用于管理列表的ActiveRecord插件.zip

    acts_as_list, 用于管理列表的ActiveRecord插件 ActsAsList描述这个 acts_as 扩展提供了对列表中的多个对象进行排序和重新排序的功能。 具有指定的类的类需要在映射的数据库表上定义为整数的position 列。 0.8.0升级...

    acts_as_category:想想acts_as_tree +权限

    #ActsAsCategory acts_as_category (Version 2.0 beta)acts_as_category,是acts_as插件在acts_as_tree风格的Ruby on Rails的ActiveRecord的模式,但有一些额外的功能,以及多种便捷视图助手。例子(有关实例方法和...

    acts_as_paranoid

    参考链接:[acts_as_paranoid官方文档](https://github.com/ActsAsParanoid/acts_as_paranoid) 通过学习和使用"acts_as_paranoid",开发者能够提升数据安全性,同时保持数据库的整洁,避免了因错误操作导致的数据不...

    rails_admin_acts_as_list:rails_admin插件以对记录进行排序

    介绍插件,用于对记录进行排序(使用 gem)安装要启用rails_admin_acts_as_list,请将以下内容添加到您的Gemfile : gem 'rails_admin_acts_as_list'gem 'rails_admin' 重要提示: rails_admin_acts_as_list之前必须...

    acts_as_restful_list:就像acts_as_list一样,但很安静

    acts_as_restful_list 就像acts_as_list 一样,但不必使用非标准方法调用(如insert_at)来弄乱您的代码,acts_as_restful_list 使管理列表变得简单。 您可以像更新其他任何内容一样更新 position 属性,其余的都...

    用acts_as_rateable实现简单的打分功能

    在Ruby on Rails框架中,`acts_as_rateable`是一个非常实用的插件,它允许用户对模型进行评分,从而实现简单的打分功能。这个插件是Rails社区中的一个开源项目,旨在简化应用中的评分系统集成。在本篇讨论中,我们将...

    acts_as_nested_set的增强版BetterNestedSet

    《深入理解BetterNestedSet:acts_as_nested_set的增强版》 在Ruby on Rails开发中,数据结构的选择对于数据库操作的效率至关重要。其中,Nested Set模型是一种常用的数据组织方式,尤其适用于管理具有层级关系的...

    Api-acts_as_api.zip

    Api-acts_as_api.zip,使在rails中创建api响应变得简单和有趣,一个api可以被认为是多个软件设备之间通信的指导手册。例如,api可用于web应用程序之间的数据库通信。通过提取实现并将数据放弃到对象中,api简化了编程...

    active_record-acts_as, 模拟activerecord模型的多表继承.zip

    active_record-acts_as, 模拟activerecord模型的多表继承 插件开发已经移动这个项目的积极发展已经转移到了的krautcomputing fork 。... ActiveRecord::ActsAs这是对 acts_as_relation的重构。模拟用于Acti

    acts_as_paranoid:ActiveRecord插件可让您隐藏和还原记录,而无需实际删除它们

    使徒行传 一个Rails插件来添加软删除。...用法安装gem: gem 'acts_as_paranoid' , '~&gt; 0.7.0' bundle install创建迁移bin/rails generate migration AddDeletedAtToParanoiac deleted_at:datetime:index启用ActsAs

    acts_as_sane_tree:用于ActiveRecord和PostgreSQLSane树构建器

    acts_as_sane_tree (用一些理智的方法建造树木) 在Postgresql&gt; = 8.4的系统上,这是对act_as_tree的替代。这提供了什么 建立树木的快速方法。哪个版本的 轨道〜&gt; 4.1.0 轨道〜&gt; 4.0.0 导轨〜&gt; 3.2.0 轨道〜&gt; 3.1.0...

    spring-acts

    spring-acts

    actions_as_commentable:ActiveRecord acts_as_commentable插件

    gem 'acts_as_commentable' , git: 'git@github.com:jackdempsey/acts_as_commentable.git' , branch: '2.x' 生成器 Rails 3+ rails g comment Rails script/generate comment 然后迁移数据库以添加注释模型:...

    acts_as_shopping_cart:简单的购物车实施

    gem 'acts_as_shopping_cart', :github =&gt; 'dabit/acts_as_shopping_cart', :branch =&gt; '0-1-x' 并运行捆绑器 bundle install 滑轨4 只需将其包含在您的Gemfile中即可: gem 'acts_as_shopping_cart', '~&gt; ...

    acts_as_aliased:扩展 ActiveRecord

    gem 'acts_as_aliased' 更新包后,运行 rails generate acts_as_aliased:install rake db:migrate 这将创建一个新表aliases 。 用法 假设您有一个需要别名的模型Company ,因为公司名称有不同的版本。 使用acts_as...

    acts_as_liked:向任何 Active Record 模型添加类似功能

    gem 'acts_as_liked' 然后执行: $ bundle 运行生成器: $ rails generate acts_as_liked 并且不要忘记迁移您的数据库 $ rake db:migrate 用法 可爱的模特 将acts_as_likeable添加到任何模型,它的实例可以被...

    acts_as_owner.rb:Rails 的简单所有权解决方案

    rails plugin install git://github.com/cyril/acts_as_owner.git 入门 配置模型 所有者模型只是必须声明得益于acts_as_owner ,通过一个块传递的每个可拥有对象(使用owns_one或owns_many方法)。 例子 class

    acts_as_imageable:轨道的多态图像

    app/uploaders/acts_as_imageable/file_uploader.rb载波上传器。 在此处添加版本和流程 app/models/concerns/acts_as_imageable/images_attribute.rb将图像属性添加到可成像对象的模型问题 db/migrate/...

Global site tag (gtag.js) - Google Analytics